SlideShare a Scribd company logo
prepare for…
From mess to masterpiece
refactoring done right
@SvenRuppert
@SvenRuppert
has been coding java since 1996
Projects in the field of:
•Automobile-industry
•Energy
•Finance / Leasing
•Space- Satellit-
•Government / UN / World-bank
Where?
•Europe
•Asia - from India up to Malaysia
2
Our journey today
what is the situation…..
3
@SvenRuppert
4
@SvenRuppertAt the time I started - 3 yrs ago
Codebase is > 13 years old
no test coverage
Code Lords
nearly 15% are retired soon
over 50% are since 15 yrs in the company
the developers learned Java at this project
hiring only students
the first feeling was like ……
5
@SvenRuppertAt the time I started - 3 yrs ago
6
What is part of a refactoring ?
the team
the source code
the processes
the project management
the knowledge
budget and time line
infrastructure
@SvenRuppert
7
What is part of a refactoring ?
the team
the source code the processes
the project management
the knowledge
budget and time line
}
}
team transformation
C-level transformation
infrastructure
@SvenRuppert
prepare for
Refactoring - the first steps
without this you should not start
8
@SvenRuppert
9
@SvenRuppertfirst steps - Start Small
10
@SvenRuppertfirst steps - Think Bigger
11
@SvenRuppertfirst steps - Build a Team
12
@SvenRuppertfirst steps - build trust
prepare for
Refactoring - the way of working
start with individual responsibility
13
@SvenRuppert
14
@SvenRuppertThe way of working
20% Time have time to play or try
start learning how to practice it ?
Closed Source versus Open Source
work from everywhere at your time
we started step by step
15
@SvenRuppertwork from everywhere
16
@SvenRuppertwork from everywhere
change your environment
use Messenger like Slack avoid mails
remote meetings with zoom
remote Pair-Programming
work async.
work at your time that is the best for you
17
@SvenRuppertwork from everywhere
work at your time that is the best for you
my „normal“ day…
working05AM to 07AM
breakfast with the family07AM to 09AM
working09AM to 12AM
playing with my son12AM to 07PM
playing with my wife07PM to 09PM
working09PM to 11PM
and yes… I need only 6h sleep ;-)
18
@SvenRuppertwork from everywhere
work at your time that is the best for you
my „normal“ day…
working05AM to 07AM
working09AM to 12AM
working09PM to 11PM
working with Asia
working with Europe
working with US
19
@SvenRuppertThe way of working
why you should do it?20% Time
lost in daily business
20
@SvenRuppertThe way of working
how to make it useful ?
example : POC with the team in the Mountains
for the developer
for the company
20% Time
prepare for
Refactoring - Divide your code
what is the part you are earning money with
21
@SvenRuppert
22
@SvenRuppertClosed- versus Open Source
Analyzing the existing Code
in our case : a lot of infrastructure…
..with this we are not earning money
we divided the
code base
dev. environment
23
@SvenRuppertClosed- versus Open Source
we divided the
code base dev. environment
could write articles about it
discuss at conferences
will lead to better documentation
out of company rules
free choice of tools
higher motivation
prepare for
Refactoring - the reactions
don´t forget the team you are working with
24
@SvenRuppert
25
@SvenRuppertThe way of working
Start Learning again
for example:
functional
add a new Language
focus on a new paradigm
but not everyone want to learn
or better…. some are learning faster
reactive
this sometimes leads to …..
reactions….
26
@SvenRuppertThe way of working
Start Learning again
this sometimes leads to ….. reactions….
running away
27
@SvenRuppertThe way of working
Start Learning again
this sometimes leads to ….. reactions….
expecting something
28
@SvenRuppertThe way of working
Start Learning again
this sometimes leads to ….. reactions….
feeling the near end
29
@SvenRuppertThe way of working
Start Learning again
this sometimes leads to ….. reactions….
or only
feeling to old
30
@SvenRuppertThe way of working
Start Learning again
this sometimes leads to ….. reactions….
you have to deal with this
if you don´t want
to loose them
make them
happy again
How we solved
this?
prepare for
Refactoring - Projectmanagement
one size fit´s all ?
31
@SvenRuppert
32
@SvenRuppertThe way of working
we are a product company
with a lot of LTS contracts
we created three streams
Consultants - play and throw away
Core Developers - collect and clean
LTS Developers - keep alive
Why ?
33
@SvenRuppertThe way of working
Consultants - play and throw away
Core Developer - collect and clean
LTS Developer - keep alive Why ?
some want to learn and experiment
some need more stabil environments
some did not want to change something
34
@SvenRuppertThe way of working
Consultants - play and throw away
Core Developer - collect and clean
LTS Developer - keep alive
Why ?
some want to learn and experiment
some need more stabil environments
some did not want to change something
amount of hours paid by the customer
rated on hours the systems are stabil
fixed income - bonus based on Change Request
35
@SvenRuppertThe way of working
Consultants - play and throw away
Core Developer - collect and clean
LTS Developer - keep alive
SCRUM
Kanban
customer driven
roadmap driven
36
@SvenRuppertThe way of working
SCRUM
Kanban
Consultants
LTS - Developers
Core - Developers Core - Developers
Fire
Consultants
37
@SvenRuppertThe way of working
SCRUM
Kanban
Consultants
LTS - Developers
Core - Developers
Consultants Consultants Consultants
LTS - Developers LTS - Developers
Core - Developers Core - Developers
time based planning fixed size time slots
version based dynamic size time slots
prepare for
Refactoring - Start learning again
learn how to learn together with a team again
38
@SvenRuppert
39
@SvenRuppertKnowledge Sharing
Consultants
LTS - Developers
Core - Developers
build a source of knowledge
40
@SvenRuppertKnowledge Sharing
Consultants
LTS - Developers
Core - Developers
Hacking session
Articles / Blogs
Screencasts
Refactoring Sessions
POC
41
@SvenRuppertKnowledge Sharing
How to motivate your team to do it ?
explain it !!
prepare for
Refactoring - Technologies
choose your weapons
42
@SvenRuppert
43
@SvenRuppertTechnical Migrations
if you ask the consultants…
to scale or change you need at least … ;-)
NoSQL
Events
Akka / Scala
Reactive
Functional
maybe ;-)
44
@SvenRuppertTechnical Transformation
Swing Vaadin
HashMap Hazelcast - Map
JDBC - ResultSet Speedment - Streams
what is the right technology for your team?
what is the right order?
Java OOP Java FRP
45
@SvenRuppertTechnical Transformation
what is the right technology for your team?
what is the right order?
reduce complexity
scale
the team could work with
a lot more….
start with new modules ?
start with the oldest one ?
most komplex one?
… or ….
46
@SvenRuppertTechnical Transformation
on thing that would limit your speed…
time
number of versions
v1
v2
stabilize
47
@SvenRuppertTechnical Transformation
on thing that would limit your speed…
time
number of versions
v2
stabilize
delta t compared
to project lifetime
prepare for
Refactoring - Safety belt
choose your weapons
48
@SvenRuppert
49
@SvenRuppertQM / QS - TDD
Do you have bugs in your code ?
since years
you are
working hard
on this….
no
50
@SvenRuppertQM / QS - TDD
Codebase is > 13 years old
no test coverage
how to decrease complexity?
remember….
how to start?
what is the right point to start?
how to increase the quality of the tests?
51
TDD with jUnit @SvenRuppert
are you using jUnit?
assume that the following would make sense.. ;-)
public class Service {

public int add(int a, int b){

if(a<2){

return (a+b) * -1;

} else {

return a+b;

}

}

}
How many tests
you will need ?
it depends ;-)
52
TDD with jUnit @SvenRuppert
public class Service {

public int add(int a, int b){

if(a<2){

return (a+b) * -1;

} else {

return a+b;

}

}

}
How many tests
you will need ?
for line 100% coverage 2
but will this be enough? maybe ;-)
how to find out, what will be enough?
how to find the right tests?
it depends ;-)
53
Mutation Testing @SvenRuppert
generating the mutants and
practical TDD with Mutation Testing
running all junit tests
check the reports
write more / better tests
loop until quality target reached
54
Mutation Testing - Hello World @SvenRuppert
public class Service {
public int add(int a, int b){
if (a<2) { return (a+b) * -1; } 

else { return a+b; }

}

} 100% Line Coverage… and…
@Test

public void testAdd001() throws Exception {

final int add = new Service().add(0, 0);

Assertions.assertThat(add).isEqualTo(0);

}
@Test

public void testAdd002() throws Exception {

final int add = new Service().add(3, 0);

Assertions.assertThat(add).isEqualTo(3);

}
55
Mutation Testing - Hello World @SvenRuppert
final int add = new Service().add(0, 0);

Assertions.assertThat(add).isEqualTo(0);
final int add = new Service().add(3, 0);

Assertions.assertThat(add).isEqualTo(3);
56
Mutation Testing - Hello World @SvenRuppert
final int add = new Service().add(0, 0);
final int add = new Service().add(3, 0);
>> Generated mutations Killed 3
57
Mutation Testing - Hello World @SvenRuppert
final int add = new Service().add(0, 0);
final int add = new Service().add(3, 0);
>> Generated mutations Killed 3
58
Mutation Testing - in short words @SvenRuppert
mutation testing is an add on to normal jUnit TDD
tools are supporting it well
generating and running all tests are time consuming
but most important
will effect your project structure
59
Mutation Testing - Lesson Learned @SvenRuppert
mutation tests are often leading to
…cleaner code compared to jUnit only
60
Mutation Testing - Lesson Learned @SvenRuppert
public static final String[] discardCommonPrefix(String a, String b) {
String[] ret = { a, b };
int l = a.length() < b.length() ? a.length() : b.length();
for (int i = 0; i < l; i++) {
if (a.charAt(i) == b.charAt(i)) {
if (i + 1 < l) { ret[0] = a.substring(i + 1); ret[1] = b.substring(i + 1); }
else {
if (a.length() < b.length()) { ret[0] = ""; ret[1] = b.substring(i + 1); }
if (a.length() == b.length()) { ret[0] = ""; ret[1] = „"; }
if (a.length() > b.length()) { ret[0] = a.substring(i + 1); ret[1] = „"; }
}
} else break;
}
return ret;
}
61
Mutation Testing - Lesson Learned @SvenRuppert
public String[] discardCommonPrefix(String a, String b) {
final String[] ret = new String[2];
int l;
if (a.length() < b.length()) { l = a.length(); }
else { l = b.length(); }
int position = 0;
for (; position < l; position++) {
final char charA = a.charAt(position);
final char charB = b.charAt(position);
if (charA != charB) { break; }
}
if (position >= a.length()) { ret[0] = ""; }
else { ret[0] = a.substring(position); }
if (position >= b.length()) { ret[1] = ""; }
else { ret[1] = b.substring(position); }
return ret;
}
62
Mutation Testing - Lesson Learned @SvenRuppert
Version 1 Version 2
for {
if {
if
else {
if
if
if
}
} else
}
if else
for {
if
}
if else
if else
63
Example of useless Code @SvenRuppert
Functions
how use Functions…
@SvenRuppert
Functions - Java8
65
@SvenRuppert
Functions - Java8
66
@SvenRuppert
Functions - Java8
67
@SvenRuppert
prepare for
Refactoring - Design Pattern
start developing design pattern again
68
@SvenRuppert
NestedBuilder - The Beginning
69
@SvenRuppert
NestedBuilder - The Beginning
70
@SvenRuppert
Car car = Car.newBuilder()

.withEngine(engine)

.withWheelList(wheels)

.build();
Engine engine = Engine.newBuilder().withPower(100).withType(5).build();
Wheel wheel1 = Wheel.newBuilder().withType(2).withColour(3).withSize(4).build(); 

Wheel wheel2 = Wheel.newBuilder().withType(2).withColour(3).withSize(4).build();

Wheel wheel3 = Wheel.newBuilder().withType(2).withColour(3).withSize(4).build();
List<Wheel> wheels = new ArrayList<>();

wheels.add(wheel1);

wheels.add(wheel2);

wheels.add(wheel3);}
NestedBuilder - The Beginning
71
@SvenRuppert
Car car = Car.newBuilder()

.withEngine(engine)

.withWheelList(wheels)

.build();
Engine engine = Engine.newBuilder().withPower(100).withType(5).build();
Wheel wheel1 = Wheel.newBuilder().withType(2).withColour(3).withSize(4).build(); 

Wheel wheel2 = Wheel.newBuilder().withType(2).withColour(3).withSize(4).build();

Wheel wheel3 = Wheel.newBuilder().withType(2).withColour(3).withSize(4).build();
List<Wheel> wheels = new ArrayList<>();

wheels.add(wheel1);

wheels.add(wheel2);

wheels.add(wheel3);
NestedBuilder - The Beginning
72
@SvenRuppert
Car car = Car.newBuilder()

.withEngine(engine)

.withWheelList(wheels)

.build();
Engine engine = Engine.newBuilder().withPower(100).withType(5).build();
Wheel wheel1 = Wheel.newBuilder().withType(2).withColour(3).withSize(4).build(); 

Wheel wheel2 = Wheel.newBuilder().withType(2).withColour(3).withSize(4).build();

Wheel wheel3 = Wheel.newBuilder().withType(2).withColour(3).withSize(4).build();
//List<Wheel> wheels = new ArrayList<>();

// wheels.add(wheel1);

// wheels.add(wheel2);

// wheels.add(wheel3);
List<Wheel> wheelList = WheelListBuilder.newBuilder()

.withNewList()

.addWheel(wheel1)

.addWheel(wheel2)

.addWheel(wheel3)

.build(); //more robust if you add tests at build()
}
}
how to combine ?
List<Wheel> wheels = new ArrayList<>();

wheels.add(wheel1);

wheels.add(wheel2);

wheels.add(wheel3);
NestedBuilder - The Beginning
73
@SvenRuppert
Car car = Car.newBuilder()

.withEngine(engine)

.withWheelList(wheels)

.build();
Engine engine = Engine.newBuilder().withPower(100).withType(5).build();
Wheel wheel1 = Wheel.newBuilder().withType(2).withColour(3).withSize(4).build(); 

Wheel wheel2 = Wheel.newBuilder().withType(2).withColour(3).withSize(4).build();

Wheel wheel3 = Wheel.newBuilder().withType(2).withColour(3).withSize(4).build();
List<Wheel> wheelList = WheelListBuilder.newBuilder()

.withNewList()

.addWheel(wheel1)

.addWheel(wheel2)

.addWheel(wheel3)

.build();
}
}
how to combine ?
NestedBuilder - The Beginning
74
@SvenRuppert
Car car = Car.newBuilder()

.withEngine(engine)

.withWheelList(wheels)

.build();
Engine engine = Engine.newBuilder().withPower(100).withType(5).build();
// Wheel wheel1 = Wheel.newBuilder().withType(2).withColour(3).withSize(4).build(); 

// Wheel wheel2 = Wheel.newBuilder().withType(2).withColour(3).withSize(4).build();

// Wheel wheel3 = Wheel.newBuilder().withType(2).withColour(3).withSize(4).build();
// List<Wheel> wheelList = WheelListBuilder.newBuilder()

.withNewList()

.addWheel(wheel1)

.addWheel(wheel2)

.addWheel(wheel3)

.build();
List<Wheel> wheels = wheelListBuilder

.addWheel().withType(1).withSize(2).withColour(2).addWheelToList()

.addWheel().withType(1).withSize(2).withColour(2).addWheelToList()

.addWheel().withType(1).withSize(2).withColour(2).addWheelToList()

.addWheel().withType(1).withSize(2).withColour(2).addWheelToList()

.build();
NestedBuilder - The Beginning
75
@SvenRuppert
Car car = Car.newBuilder()

.withEngine(engine)

.withWheelList(wheels)

.build();
Engine engine = Engine.newBuilder().withPower(100).withType(5).build();
List<Wheel> wheels = wheelListBuilder

.addWheel().withType(1).withSize(2).withColour(2).addWheelToList()

.addWheel().withType(1).withSize(2).withColour(2).addWheelToList()

.addWheel().withType(1).withSize(2).withColour(2).addWheelToList()

.addWheel().withType(1).withSize(2).withColour(2).addWheelToList()

.build();
WheelBuilder
WheelListBuilder
NestedBuilder - The Beginning
76
@SvenRuppert
Car car = Car.newBuilder()

.withEngine(engine)

.withWheelList(wheels)

.build();
Engine engine = Engine.newBuilder().withPower(100).withType(5).build();
List<Wheel> wheels = wheelListBuilder

.addWheel().withType(1).withSize(2).withColour(2).addWheelToList()

.addWheel().withType(1).withSize(2).withColour(2).addWheelToList()

.addWheel().withType(1).withSize(2).withColour(2).addWheelToList()

.addWheel().withType(1).withSize(2).withColour(2).addWheelToList()

.build();
now we have to combine all
Car car = Car.newBuilder()

.addEngine().withPower(100).withType(5).done()

.addWheels()

.addWheel().withType(1).withSize(2).withColour(2).addWheelToList()

.addWheel().withType(1).withSize(2).withColour(2).addWheelToList()

.addWheel().withType(1).withSize(2).withColour(2).addWheelToList()

.addWheel().withType(1).withSize(2).withColour(2).addWheelToList()

.done()

.build();
NestedBuilder - The Pattern
77
@SvenRuppert
public abstract class NestedBuilder<T, V> {
protected T parent;
public abstract V build()
public <P extends NestedBuilder<T, V>> P 

withParentBuilder(T parent) {

this.parent = parent;

return (P) this;

}
parent will connect itself…
NestedBuilder - The Pattern
78
@SvenRuppert
public abstract class NestedBuilder<T, V> {
public T done() {
Class<?> parentClass = parent.getClass();
try {

V build = this.build();

String methodname = "with" + build.getClass().getSimpleName();

Method method = parentClass.getDeclaredMethod(

methodname, build.getClass());

method.invoke(parent, build);

} catch (NoSuchMethodException 

| IllegalAccessException | InvocationTargetException e) {

e.printStackTrace();

}
}
connect itself with parent
NestedBuilder - The Pattern
79
@SvenRuppert
the basic steps in short words
the Parent-Builder will hold the Child-Builder
the Parent-Builder will have a addChild - Method
the Child-Builder will extend the NestedBuilder
the rest could be generated with a 

default Builder-Generator
NestedBuilder - The Pattern
80
@SvenRuppert
public class Parent {

private KidA kidA;

private KidB kidB;

//snipp.....

public static final class Builder {

private KidA kidA;

private KidB kidB;

// to add manually

private KidA.Builder builderKidA = KidA.newBuilder().withParentBuilder(this);

private KidB.Builder builderKidB = KidB.newBuilder().withParentBuilder(this);



public KidA.Builder addKidA() {

return this.builderKidA;

}

public KidB.Builder addKidB() {

return this.builderKidB;

}

//---------
connect itself with child
switch to Child-Builder
NestedBuilder - The Pattern
81
@SvenRuppert
only extends on Child-Builder
public static final class Builder 

extends NestedBuilder<Parent.Builder, KidA> {
NestedBuilder - The Pattern
82
@SvenRuppert
Parent build = Parent.newBuilder()



.addKidA().withNote("A").done()

.addKidB().withNote("B").done()



.build();

System.out.println("build = " + build);
and a child could be a parent in the same time
Parent build = Parent.newBuilder()

.addKidA().withNote("A")
.addKidB().withNote("B").done()
.done()

.build();
System.out.println("build = " + build);

Refactoring example
based on Java8
@SvenRuppert
84
@SvenRuppertJava8 - Functional Interfaces - Example
typical legacy implementation
85
@SvenRuppertJava8 - Functional Interfaces - Example
typical legacy implementation
86
@SvenRuppertJava8 - Functional Interfaces - Example
87
@SvenRuppertJava8 - Functional Interfaces - Example
88
@SvenRuppertJava8 - Functional Interfaces - Example
89
@SvenRuppertJava8 - Functional Interfaces - Example
90
@SvenRuppertJava8 - Functional Interfaces - Example
91
@SvenRuppertJava8 - Functional Interfaces - Example
Sourcecode is on github
Interpreter - pre Java8
92
@SvenRuppert
Interpreter - pre Java8
93
@SvenRuppert
Interpreter - pre Java8
94
@SvenRuppert
Interpreter - pre Java8
95
@SvenRuppert
Interpreter - Java8 - Java9
96
@SvenRuppert
Interpreter - Java8 - Java9
97
@SvenRuppert
Main Idea - DataStructure to Function
Memoizing
partial cache-ing ?
@SvenRuppert
full example and code
http://www.functional-reactive.org/
prepare for
Refactoring - Clean your code
nano refactoring on language level
99
@SvenRuppert
clean your code @SvenRuppert
delete JavaDoc
use final for Attributes as much as possible
replace loops with streams
extract Functional Interfaces
remove anonymous classes
use everywhere the same language level
Why ?
clean your code @SvenRuppert
delete JavaDoc
use final for Attributes as much as possible
replace loops with streams
extract Functional Interfaces
remove anonymous classes
use everywhere the same language level
Why ?
know the part you want to refactor
homogeneous sources are better for machines
prepare for
Refactoring - Summary
the full picture
102
@SvenRuppert
Refactoring - Summary
103
@SvenRuppert
prepare your team
change the way of working
work on your project management
build your safety belt - mutation testing
divide and conquer - @Inject
build design pattern again
extract cross functionality - Proxy's
clean your code
prepare for
Management - Summary
the full picture for the C-Level
104
@SvenRuppert
Management - Summary
105
@SvenRuppert
Now it is time to relax again ;-)
Problem solved !
Summary
106
@SvenRuppert
places to read more about it
www.functional-reactive.org
www.java-9.org
or contact me ;-) @SvenRuppert
Thank You !!!

More Related Content

Similar to From Mess To Masterpiece - JFokus 2017

Who Is A DevOps Engineer? | DevOps Skills You Must Master | DevOps Engineer M...
Who Is A DevOps Engineer? | DevOps Skills You Must Master | DevOps Engineer M...Who Is A DevOps Engineer? | DevOps Skills You Must Master | DevOps Engineer M...
Who Is A DevOps Engineer? | DevOps Skills You Must Master | DevOps Engineer M...
Edureka!
 
My Dad Won't Buy Me DevOps
My Dad Won't Buy Me DevOpsMy Dad Won't Buy Me DevOps
My Dad Won't Buy Me DevOps
XebiaLabs
 
What's an SRE at Criteo - Meetup SRE Paris
What's an SRE at Criteo - Meetup SRE ParisWhat's an SRE at Criteo - Meetup SRE Paris
What's an SRE at Criteo - Meetup SRE Paris
Clément Michaud
 
DOES14: Scott Prugh, CSG - DevOps and Lean in Legacy Environments
DOES14: Scott Prugh, CSG - DevOps and Lean in Legacy EnvironmentsDOES14: Scott Prugh, CSG - DevOps and Lean in Legacy Environments
DOES14: Scott Prugh, CSG - DevOps and Lean in Legacy Environments
DevOps Enterprise Summmit
 
DOES14 - David Ashman, Blackboard Learn - Keep Your Head in the Clouds Tuesda...
DOES14 - David Ashman, Blackboard Learn - Keep Your Head in the Clouds Tuesda...DOES14 - David Ashman, Blackboard Learn - Keep Your Head in the Clouds Tuesda...
DOES14 - David Ashman, Blackboard Learn - Keep Your Head in the Clouds Tuesda...
DevOps Enterprise Summmit
 
DOES14 - David Ashman - Blackboard Learn - Keep Your Head in the Clouds
DOES14 - David Ashman - Blackboard Learn - Keep Your Head in the CloudsDOES14 - David Ashman - Blackboard Learn - Keep Your Head in the Clouds
DOES14 - David Ashman - Blackboard Learn - Keep Your Head in the Clouds
Gene Kim
 
DevOpsGuys FutureDecoded 2016 - is DevOps the Answer
DevOpsGuys FutureDecoded 2016 - is DevOps the AnswerDevOpsGuys FutureDecoded 2016 - is DevOps the Answer
DevOpsGuys FutureDecoded 2016 - is DevOps the Answer
DevOpsGroup
 
Cs 568 Spring 10 Lecture 5 Estimation
Cs 568 Spring 10  Lecture 5 EstimationCs 568 Spring 10  Lecture 5 Estimation
Cs 568 Spring 10 Lecture 5 Estimation
Lawrence Bernstein
 
The NRB Group mainframe day 2021 - DevOps on Z - Jerome Klimm - Benoit Ebner
The NRB Group mainframe day 2021 - DevOps on Z - Jerome Klimm - Benoit EbnerThe NRB Group mainframe day 2021 - DevOps on Z - Jerome Klimm - Benoit Ebner
The NRB Group mainframe day 2021 - DevOps on Z - Jerome Klimm - Benoit Ebner
NRB
 
Going deep (learning) with tensor flow and quarkus
Going deep (learning) with tensor flow and quarkusGoing deep (learning) with tensor flow and quarkus
Going deep (learning) with tensor flow and quarkus
Red Hat Developers
 
Metrics driven dev ops 2017
Metrics driven dev ops 2017Metrics driven dev ops 2017
Metrics driven dev ops 2017
Jerry Tan
 
Automate across Platform, OS, Technologies with TaaS
Automate across Platform, OS, Technologies with TaaSAutomate across Platform, OS, Technologies with TaaS
Automate across Platform, OS, Technologies with TaaS
Anand Bagmar
 
Jan de Vries - How to convince your boss that it is DevOps that he wants
Jan de Vries - How to convince your boss that it is DevOps that he wantsJan de Vries - How to convince your boss that it is DevOps that he wants
Jan de Vries - How to convince your boss that it is DevOps that he wants
Agile Lietuva
 
DevOPs Transformation Workshop
DevOPs Transformation WorkshopDevOPs Transformation Workshop
DevOPs Transformation Workshop
Jules Pierre-Louis
 
Making the business case for DevOps
Making the business case for DevOpsMaking the business case for DevOps
Making the business case for DevOps
Martin Croker
 
Continuous Deployment To The Cloud With Spring Cloud Pipelines @WarsawCloudNa...
Continuous Deployment To The Cloud With Spring Cloud Pipelines @WarsawCloudNa...Continuous Deployment To The Cloud With Spring Cloud Pipelines @WarsawCloudNa...
Continuous Deployment To The Cloud With Spring Cloud Pipelines @WarsawCloudNa...
Marcin Grzejszczak
 
rnd teams.pptx
rnd teams.pptxrnd teams.pptx
rnd teams.pptx
Alexander Tokarev
 
Continuous Deployment To The Cloud
Continuous Deployment To The CloudContinuous Deployment To The Cloud
Continuous Deployment To The Cloud
Marcin Grzejszczak
 
How to test a Mainframe Application
How to test a Mainframe ApplicationHow to test a Mainframe Application
How to test a Mainframe Application
Michael Erichsen
 
Automate across Platform, OS, Technologies with TaaS
Automate across Platform, OS, Technologies with TaaSAutomate across Platform, OS, Technologies with TaaS
Automate across Platform, OS, Technologies with TaaS
Thoughtworks
 

Similar to From Mess To Masterpiece - JFokus 2017 (20)

Who Is A DevOps Engineer? | DevOps Skills You Must Master | DevOps Engineer M...
Who Is A DevOps Engineer? | DevOps Skills You Must Master | DevOps Engineer M...Who Is A DevOps Engineer? | DevOps Skills You Must Master | DevOps Engineer M...
Who Is A DevOps Engineer? | DevOps Skills You Must Master | DevOps Engineer M...
 
My Dad Won't Buy Me DevOps
My Dad Won't Buy Me DevOpsMy Dad Won't Buy Me DevOps
My Dad Won't Buy Me DevOps
 
What's an SRE at Criteo - Meetup SRE Paris
What's an SRE at Criteo - Meetup SRE ParisWhat's an SRE at Criteo - Meetup SRE Paris
What's an SRE at Criteo - Meetup SRE Paris
 
DOES14: Scott Prugh, CSG - DevOps and Lean in Legacy Environments
DOES14: Scott Prugh, CSG - DevOps and Lean in Legacy EnvironmentsDOES14: Scott Prugh, CSG - DevOps and Lean in Legacy Environments
DOES14: Scott Prugh, CSG - DevOps and Lean in Legacy Environments
 
DOES14 - David Ashman, Blackboard Learn - Keep Your Head in the Clouds Tuesda...
DOES14 - David Ashman, Blackboard Learn - Keep Your Head in the Clouds Tuesda...DOES14 - David Ashman, Blackboard Learn - Keep Your Head in the Clouds Tuesda...
DOES14 - David Ashman, Blackboard Learn - Keep Your Head in the Clouds Tuesda...
 
DOES14 - David Ashman - Blackboard Learn - Keep Your Head in the Clouds
DOES14 - David Ashman - Blackboard Learn - Keep Your Head in the CloudsDOES14 - David Ashman - Blackboard Learn - Keep Your Head in the Clouds
DOES14 - David Ashman - Blackboard Learn - Keep Your Head in the Clouds
 
DevOpsGuys FutureDecoded 2016 - is DevOps the Answer
DevOpsGuys FutureDecoded 2016 - is DevOps the AnswerDevOpsGuys FutureDecoded 2016 - is DevOps the Answer
DevOpsGuys FutureDecoded 2016 - is DevOps the Answer
 
Cs 568 Spring 10 Lecture 5 Estimation
Cs 568 Spring 10  Lecture 5 EstimationCs 568 Spring 10  Lecture 5 Estimation
Cs 568 Spring 10 Lecture 5 Estimation
 
The NRB Group mainframe day 2021 - DevOps on Z - Jerome Klimm - Benoit Ebner
The NRB Group mainframe day 2021 - DevOps on Z - Jerome Klimm - Benoit EbnerThe NRB Group mainframe day 2021 - DevOps on Z - Jerome Klimm - Benoit Ebner
The NRB Group mainframe day 2021 - DevOps on Z - Jerome Klimm - Benoit Ebner
 
Going deep (learning) with tensor flow and quarkus
Going deep (learning) with tensor flow and quarkusGoing deep (learning) with tensor flow and quarkus
Going deep (learning) with tensor flow and quarkus
 
Metrics driven dev ops 2017
Metrics driven dev ops 2017Metrics driven dev ops 2017
Metrics driven dev ops 2017
 
Automate across Platform, OS, Technologies with TaaS
Automate across Platform, OS, Technologies with TaaSAutomate across Platform, OS, Technologies with TaaS
Automate across Platform, OS, Technologies with TaaS
 
Jan de Vries - How to convince your boss that it is DevOps that he wants
Jan de Vries - How to convince your boss that it is DevOps that he wantsJan de Vries - How to convince your boss that it is DevOps that he wants
Jan de Vries - How to convince your boss that it is DevOps that he wants
 
DevOPs Transformation Workshop
DevOPs Transformation WorkshopDevOPs Transformation Workshop
DevOPs Transformation Workshop
 
Making the business case for DevOps
Making the business case for DevOpsMaking the business case for DevOps
Making the business case for DevOps
 
Continuous Deployment To The Cloud With Spring Cloud Pipelines @WarsawCloudNa...
Continuous Deployment To The Cloud With Spring Cloud Pipelines @WarsawCloudNa...Continuous Deployment To The Cloud With Spring Cloud Pipelines @WarsawCloudNa...
Continuous Deployment To The Cloud With Spring Cloud Pipelines @WarsawCloudNa...
 
rnd teams.pptx
rnd teams.pptxrnd teams.pptx
rnd teams.pptx
 
Continuous Deployment To The Cloud
Continuous Deployment To The CloudContinuous Deployment To The Cloud
Continuous Deployment To The Cloud
 
How to test a Mainframe Application
How to test a Mainframe ApplicationHow to test a Mainframe Application
How to test a Mainframe Application
 
Automate across Platform, OS, Technologies with TaaS
Automate across Platform, OS, Technologies with TaaSAutomate across Platform, OS, Technologies with TaaS
Automate across Platform, OS, Technologies with TaaS
 

More from Sven Ruppert

JUnit5 Custom TestEngines intro - version 2020-06
JUnit5 Custom TestEngines intro - version 2020-06JUnit5 Custom TestEngines intro - version 2020-06
JUnit5 Custom TestEngines intro - version 2020-06
Sven Ruppert
 
Hidden pearls for High-Performance-Persistence
Hidden pearls for High-Performance-PersistenceHidden pearls for High-Performance-Persistence
Hidden pearls for High-Performance-Persistence
Sven Ruppert
 
Vaadin Flow - How to start - a short intro for Java Devs
Vaadin Flow - How to start - a short intro for Java DevsVaadin Flow - How to start - a short intro for Java Devs
Vaadin Flow - How to start - a short intro for Java Devs
Sven Ruppert
 
Functional Reactive With Core Java - Voxxed Melbourne
Functional Reactive With Core Java - Voxxed MelbourneFunctional Reactive With Core Java - Voxxed Melbourne
Functional Reactive With Core Java - Voxxed Melbourne
Sven Ruppert
 
Functional Reactive with Core Java - Workshop - Slides
Functional Reactive with Core Java - Workshop - SlidesFunctional Reactive with Core Java - Workshop - Slides
Functional Reactive with Core Java - Workshop - Slides
Sven Ruppert
 
Functional reactive-talk 20170301-001
Functional reactive-talk 20170301-001Functional reactive-talk 20170301-001
Functional reactive-talk 20170301-001
Sven Ruppert
 
From Jurassic Park to Microservices
From Jurassic Park to MicroservicesFrom Jurassic Park to Microservices
From Jurassic Park to Microservices
Sven Ruppert
 
From jUnit to Mutationtesting
From jUnit to MutationtestingFrom jUnit to Mutationtesting
From jUnit to Mutationtesting
Sven Ruppert
 
DI Frameworks - hidden pearls
DI Frameworks - hidden pearlsDI Frameworks - hidden pearls
DI Frameworks - hidden pearls
Sven Ruppert
 
Warum ich so auf das c von cdi stehe
Warum ich so auf das c von cdi steheWarum ich so auf das c von cdi stehe
Warum ich so auf das c von cdi stehe
Sven Ruppert
 
Proxy deep-dive java-one_20151027_001
Proxy deep-dive java-one_20151027_001Proxy deep-dive java-one_20151027_001
Proxy deep-dive java-one_20151027_001
Sven Ruppert
 
Java8 ready for the future
Java8 ready for the futureJava8 ready for the future
Java8 ready for the future
Sven Ruppert
 
JavaFX8 TestFX - CDI
JavaFX8   TestFX - CDIJavaFX8   TestFX - CDI
JavaFX8 TestFX - CDI
Sven Ruppert
 
Java FX8 JumpStart - JUG ch - zürich
Java FX8   JumpStart - JUG ch - zürichJava FX8   JumpStart - JUG ch - zürich
Java FX8 JumpStart - JUG ch - zürich
Sven Ruppert
 
Proxy Deep Dive JUG Saxony Day 2015-10-02
Proxy Deep Dive JUG Saxony Day 2015-10-02Proxy Deep Dive JUG Saxony Day 2015-10-02
Proxy Deep Dive JUG Saxony Day 2015-10-02
Sven Ruppert
 
Proxy Deep Dive Voxxed Belgrad 2015
Proxy Deep Dive Voxxed Belgrad 2015Proxy Deep Dive Voxxed Belgrad 2015
Proxy Deep Dive Voxxed Belgrad 2015
Sven Ruppert
 

More from Sven Ruppert (16)

JUnit5 Custom TestEngines intro - version 2020-06
JUnit5 Custom TestEngines intro - version 2020-06JUnit5 Custom TestEngines intro - version 2020-06
JUnit5 Custom TestEngines intro - version 2020-06
 
Hidden pearls for High-Performance-Persistence
Hidden pearls for High-Performance-PersistenceHidden pearls for High-Performance-Persistence
Hidden pearls for High-Performance-Persistence
 
Vaadin Flow - How to start - a short intro for Java Devs
Vaadin Flow - How to start - a short intro for Java DevsVaadin Flow - How to start - a short intro for Java Devs
Vaadin Flow - How to start - a short intro for Java Devs
 
Functional Reactive With Core Java - Voxxed Melbourne
Functional Reactive With Core Java - Voxxed MelbourneFunctional Reactive With Core Java - Voxxed Melbourne
Functional Reactive With Core Java - Voxxed Melbourne
 
Functional Reactive with Core Java - Workshop - Slides
Functional Reactive with Core Java - Workshop - SlidesFunctional Reactive with Core Java - Workshop - Slides
Functional Reactive with Core Java - Workshop - Slides
 
Functional reactive-talk 20170301-001
Functional reactive-talk 20170301-001Functional reactive-talk 20170301-001
Functional reactive-talk 20170301-001
 
From Jurassic Park to Microservices
From Jurassic Park to MicroservicesFrom Jurassic Park to Microservices
From Jurassic Park to Microservices
 
From jUnit to Mutationtesting
From jUnit to MutationtestingFrom jUnit to Mutationtesting
From jUnit to Mutationtesting
 
DI Frameworks - hidden pearls
DI Frameworks - hidden pearlsDI Frameworks - hidden pearls
DI Frameworks - hidden pearls
 
Warum ich so auf das c von cdi stehe
Warum ich so auf das c von cdi steheWarum ich so auf das c von cdi stehe
Warum ich so auf das c von cdi stehe
 
Proxy deep-dive java-one_20151027_001
Proxy deep-dive java-one_20151027_001Proxy deep-dive java-one_20151027_001
Proxy deep-dive java-one_20151027_001
 
Java8 ready for the future
Java8 ready for the futureJava8 ready for the future
Java8 ready for the future
 
JavaFX8 TestFX - CDI
JavaFX8   TestFX - CDIJavaFX8   TestFX - CDI
JavaFX8 TestFX - CDI
 
Java FX8 JumpStart - JUG ch - zürich
Java FX8   JumpStart - JUG ch - zürichJava FX8   JumpStart - JUG ch - zürich
Java FX8 JumpStart - JUG ch - zürich
 
Proxy Deep Dive JUG Saxony Day 2015-10-02
Proxy Deep Dive JUG Saxony Day 2015-10-02Proxy Deep Dive JUG Saxony Day 2015-10-02
Proxy Deep Dive JUG Saxony Day 2015-10-02
 
Proxy Deep Dive Voxxed Belgrad 2015
Proxy Deep Dive Voxxed Belgrad 2015Proxy Deep Dive Voxxed Belgrad 2015
Proxy Deep Dive Voxxed Belgrad 2015
 

Recently uploaded

Empowering Growth with Best Software Development Company in Noida - Deuglo
Empowering Growth with Best Software  Development Company in Noida - DeugloEmpowering Growth with Best Software  Development Company in Noida - Deuglo
Empowering Growth with Best Software Development Company in Noida - Deuglo
Deuglo Infosystem Pvt Ltd
 
Webinar On-Demand: Using Flutter for Embedded
Webinar On-Demand: Using Flutter for EmbeddedWebinar On-Demand: Using Flutter for Embedded
Webinar On-Demand: Using Flutter for Embedded
ICS
 
Revolutionizing Visual Effects Mastering AI Face Swaps.pdf
Revolutionizing Visual Effects Mastering AI Face Swaps.pdfRevolutionizing Visual Effects Mastering AI Face Swaps.pdf
Revolutionizing Visual Effects Mastering AI Face Swaps.pdf
Undress Baby
 
Energy consumption of Database Management - Florina Jonuzi
Energy consumption of Database Management - Florina JonuziEnergy consumption of Database Management - Florina Jonuzi
Energy consumption of Database Management - Florina Jonuzi
Green Software Development
 
KuberTENes Birthday Bash Guadalajara - Introducción a Argo CD
KuberTENes Birthday Bash Guadalajara - Introducción a Argo CDKuberTENes Birthday Bash Guadalajara - Introducción a Argo CD
KuberTENes Birthday Bash Guadalajara - Introducción a Argo CD
rodomar2
 
AI Fusion Buddy Review: Brand New, Groundbreaking Gemini-Powered AI App
AI Fusion Buddy Review: Brand New, Groundbreaking Gemini-Powered AI AppAI Fusion Buddy Review: Brand New, Groundbreaking Gemini-Powered AI App
AI Fusion Buddy Review: Brand New, Groundbreaking Gemini-Powered AI App
Google
 
Using Xen Hypervisor for Functional Safety
Using Xen Hypervisor for Functional SafetyUsing Xen Hypervisor for Functional Safety
Using Xen Hypervisor for Functional Safety
Ayan Halder
 
GraphSummit Paris - The art of the possible with Graph Technology
GraphSummit Paris - The art of the possible with Graph TechnologyGraphSummit Paris - The art of the possible with Graph Technology
GraphSummit Paris - The art of the possible with Graph Technology
Neo4j
 
SWEBOK and Education at FUSE Okinawa 2024
SWEBOK and Education at FUSE Okinawa 2024SWEBOK and Education at FUSE Okinawa 2024
SWEBOK and Education at FUSE Okinawa 2024
Hironori Washizaki
 
LORRAINE ANDREI_LEQUIGAN_HOW TO USE WHATSAPP.pptx
LORRAINE ANDREI_LEQUIGAN_HOW TO USE WHATSAPP.pptxLORRAINE ANDREI_LEQUIGAN_HOW TO USE WHATSAPP.pptx
LORRAINE ANDREI_LEQUIGAN_HOW TO USE WHATSAPP.pptx
lorraineandreiamcidl
 
SMS API Integration in Saudi Arabia| Best SMS API Service
SMS API Integration in Saudi Arabia| Best SMS API ServiceSMS API Integration in Saudi Arabia| Best SMS API Service
SMS API Integration in Saudi Arabia| Best SMS API Service
Yara Milbes
 
Unveiling the Advantages of Agile Software Development.pdf
Unveiling the Advantages of Agile Software Development.pdfUnveiling the Advantages of Agile Software Development.pdf
Unveiling the Advantages of Agile Software Development.pdf
brainerhub1
 
Why Choose Odoo 17 Community & How it differs from Odoo 17 Enterprise Edition
Why Choose Odoo 17 Community & How it differs from Odoo 17 Enterprise EditionWhy Choose Odoo 17 Community & How it differs from Odoo 17 Enterprise Edition
Why Choose Odoo 17 Community & How it differs from Odoo 17 Enterprise Edition
Envertis Software Solutions
 
UI5con 2024 - Keynote: Latest News about UI5 and it’s Ecosystem
UI5con 2024 - Keynote: Latest News about UI5 and it’s EcosystemUI5con 2024 - Keynote: Latest News about UI5 and it’s Ecosystem
UI5con 2024 - Keynote: Latest News about UI5 and it’s Ecosystem
Peter Muessig
 
OpenMetadata Community Meeting - 5th June 2024
OpenMetadata Community Meeting - 5th June 2024OpenMetadata Community Meeting - 5th June 2024
OpenMetadata Community Meeting - 5th June 2024
OpenMetadata
 
A Study of Variable-Role-based Feature Enrichment in Neural Models of Code
A Study of Variable-Role-based Feature Enrichment in Neural Models of CodeA Study of Variable-Role-based Feature Enrichment in Neural Models of Code
A Study of Variable-Role-based Feature Enrichment in Neural Models of Code
Aftab Hussain
 
ALGIT - Assembly Line for Green IT - Numbers, Data, Facts
ALGIT - Assembly Line for Green IT - Numbers, Data, FactsALGIT - Assembly Line for Green IT - Numbers, Data, Facts
ALGIT - Assembly Line for Green IT - Numbers, Data, Facts
Green Software Development
 
Hand Rolled Applicative User Validation Code Kata
Hand Rolled Applicative User ValidationCode KataHand Rolled Applicative User ValidationCode Kata
Hand Rolled Applicative User Validation Code Kata
Philip Schwarz
 
openEuler Case Study - The Journey to Supply Chain Security
openEuler Case Study - The Journey to Supply Chain SecurityopenEuler Case Study - The Journey to Supply Chain Security
openEuler Case Study - The Journey to Supply Chain Security
Shane Coughlan
 
E-Invoicing Implementation: A Step-by-Step Guide for Saudi Arabian Companies
E-Invoicing Implementation: A Step-by-Step Guide for Saudi Arabian CompaniesE-Invoicing Implementation: A Step-by-Step Guide for Saudi Arabian Companies
E-Invoicing Implementation: A Step-by-Step Guide for Saudi Arabian Companies
Quickdice ERP
 

Recently uploaded (20)

Empowering Growth with Best Software Development Company in Noida - Deuglo
Empowering Growth with Best Software  Development Company in Noida - DeugloEmpowering Growth with Best Software  Development Company in Noida - Deuglo
Empowering Growth with Best Software Development Company in Noida - Deuglo
 
Webinar On-Demand: Using Flutter for Embedded
Webinar On-Demand: Using Flutter for EmbeddedWebinar On-Demand: Using Flutter for Embedded
Webinar On-Demand: Using Flutter for Embedded
 
Revolutionizing Visual Effects Mastering AI Face Swaps.pdf
Revolutionizing Visual Effects Mastering AI Face Swaps.pdfRevolutionizing Visual Effects Mastering AI Face Swaps.pdf
Revolutionizing Visual Effects Mastering AI Face Swaps.pdf
 
Energy consumption of Database Management - Florina Jonuzi
Energy consumption of Database Management - Florina JonuziEnergy consumption of Database Management - Florina Jonuzi
Energy consumption of Database Management - Florina Jonuzi
 
KuberTENes Birthday Bash Guadalajara - Introducción a Argo CD
KuberTENes Birthday Bash Guadalajara - Introducción a Argo CDKuberTENes Birthday Bash Guadalajara - Introducción a Argo CD
KuberTENes Birthday Bash Guadalajara - Introducción a Argo CD
 
AI Fusion Buddy Review: Brand New, Groundbreaking Gemini-Powered AI App
AI Fusion Buddy Review: Brand New, Groundbreaking Gemini-Powered AI AppAI Fusion Buddy Review: Brand New, Groundbreaking Gemini-Powered AI App
AI Fusion Buddy Review: Brand New, Groundbreaking Gemini-Powered AI App
 
Using Xen Hypervisor for Functional Safety
Using Xen Hypervisor for Functional SafetyUsing Xen Hypervisor for Functional Safety
Using Xen Hypervisor for Functional Safety
 
GraphSummit Paris - The art of the possible with Graph Technology
GraphSummit Paris - The art of the possible with Graph TechnologyGraphSummit Paris - The art of the possible with Graph Technology
GraphSummit Paris - The art of the possible with Graph Technology
 
SWEBOK and Education at FUSE Okinawa 2024
SWEBOK and Education at FUSE Okinawa 2024SWEBOK and Education at FUSE Okinawa 2024
SWEBOK and Education at FUSE Okinawa 2024
 
LORRAINE ANDREI_LEQUIGAN_HOW TO USE WHATSAPP.pptx
LORRAINE ANDREI_LEQUIGAN_HOW TO USE WHATSAPP.pptxLORRAINE ANDREI_LEQUIGAN_HOW TO USE WHATSAPP.pptx
LORRAINE ANDREI_LEQUIGAN_HOW TO USE WHATSAPP.pptx
 
SMS API Integration in Saudi Arabia| Best SMS API Service
SMS API Integration in Saudi Arabia| Best SMS API ServiceSMS API Integration in Saudi Arabia| Best SMS API Service
SMS API Integration in Saudi Arabia| Best SMS API Service
 
Unveiling the Advantages of Agile Software Development.pdf
Unveiling the Advantages of Agile Software Development.pdfUnveiling the Advantages of Agile Software Development.pdf
Unveiling the Advantages of Agile Software Development.pdf
 
Why Choose Odoo 17 Community & How it differs from Odoo 17 Enterprise Edition
Why Choose Odoo 17 Community & How it differs from Odoo 17 Enterprise EditionWhy Choose Odoo 17 Community & How it differs from Odoo 17 Enterprise Edition
Why Choose Odoo 17 Community & How it differs from Odoo 17 Enterprise Edition
 
UI5con 2024 - Keynote: Latest News about UI5 and it’s Ecosystem
UI5con 2024 - Keynote: Latest News about UI5 and it’s EcosystemUI5con 2024 - Keynote: Latest News about UI5 and it’s Ecosystem
UI5con 2024 - Keynote: Latest News about UI5 and it’s Ecosystem
 
OpenMetadata Community Meeting - 5th June 2024
OpenMetadata Community Meeting - 5th June 2024OpenMetadata Community Meeting - 5th June 2024
OpenMetadata Community Meeting - 5th June 2024
 
A Study of Variable-Role-based Feature Enrichment in Neural Models of Code
A Study of Variable-Role-based Feature Enrichment in Neural Models of CodeA Study of Variable-Role-based Feature Enrichment in Neural Models of Code
A Study of Variable-Role-based Feature Enrichment in Neural Models of Code
 
ALGIT - Assembly Line for Green IT - Numbers, Data, Facts
ALGIT - Assembly Line for Green IT - Numbers, Data, FactsALGIT - Assembly Line for Green IT - Numbers, Data, Facts
ALGIT - Assembly Line for Green IT - Numbers, Data, Facts
 
Hand Rolled Applicative User Validation Code Kata
Hand Rolled Applicative User ValidationCode KataHand Rolled Applicative User ValidationCode Kata
Hand Rolled Applicative User Validation Code Kata
 
openEuler Case Study - The Journey to Supply Chain Security
openEuler Case Study - The Journey to Supply Chain SecurityopenEuler Case Study - The Journey to Supply Chain Security
openEuler Case Study - The Journey to Supply Chain Security
 
E-Invoicing Implementation: A Step-by-Step Guide for Saudi Arabian Companies
E-Invoicing Implementation: A Step-by-Step Guide for Saudi Arabian CompaniesE-Invoicing Implementation: A Step-by-Step Guide for Saudi Arabian Companies
E-Invoicing Implementation: A Step-by-Step Guide for Saudi Arabian Companies
 

From Mess To Masterpiece - JFokus 2017

  • 1. prepare for… From mess to masterpiece refactoring done right @SvenRuppert
  • 2. @SvenRuppert has been coding java since 1996 Projects in the field of: •Automobile-industry •Energy •Finance / Leasing •Space- Satellit- •Government / UN / World-bank Where? •Europe •Asia - from India up to Malaysia 2
  • 3. Our journey today what is the situation….. 3 @SvenRuppert
  • 4. 4 @SvenRuppertAt the time I started - 3 yrs ago Codebase is > 13 years old no test coverage Code Lords nearly 15% are retired soon over 50% are since 15 yrs in the company the developers learned Java at this project hiring only students the first feeling was like ……
  • 5. 5 @SvenRuppertAt the time I started - 3 yrs ago
  • 6. 6 What is part of a refactoring ? the team the source code the processes the project management the knowledge budget and time line infrastructure @SvenRuppert
  • 7. 7 What is part of a refactoring ? the team the source code the processes the project management the knowledge budget and time line } } team transformation C-level transformation infrastructure @SvenRuppert
  • 8. prepare for Refactoring - the first steps without this you should not start 8 @SvenRuppert
  • 13. prepare for Refactoring - the way of working start with individual responsibility 13 @SvenRuppert
  • 14. 14 @SvenRuppertThe way of working 20% Time have time to play or try start learning how to practice it ? Closed Source versus Open Source work from everywhere at your time we started step by step
  • 16. 16 @SvenRuppertwork from everywhere change your environment use Messenger like Slack avoid mails remote meetings with zoom remote Pair-Programming work async. work at your time that is the best for you
  • 17. 17 @SvenRuppertwork from everywhere work at your time that is the best for you my „normal“ day… working05AM to 07AM breakfast with the family07AM to 09AM working09AM to 12AM playing with my son12AM to 07PM playing with my wife07PM to 09PM working09PM to 11PM and yes… I need only 6h sleep ;-)
  • 18. 18 @SvenRuppertwork from everywhere work at your time that is the best for you my „normal“ day… working05AM to 07AM working09AM to 12AM working09PM to 11PM working with Asia working with Europe working with US
  • 19. 19 @SvenRuppertThe way of working why you should do it?20% Time lost in daily business
  • 20. 20 @SvenRuppertThe way of working how to make it useful ? example : POC with the team in the Mountains for the developer for the company 20% Time
  • 21. prepare for Refactoring - Divide your code what is the part you are earning money with 21 @SvenRuppert
  • 22. 22 @SvenRuppertClosed- versus Open Source Analyzing the existing Code in our case : a lot of infrastructure… ..with this we are not earning money we divided the code base dev. environment
  • 23. 23 @SvenRuppertClosed- versus Open Source we divided the code base dev. environment could write articles about it discuss at conferences will lead to better documentation out of company rules free choice of tools higher motivation
  • 24. prepare for Refactoring - the reactions don´t forget the team you are working with 24 @SvenRuppert
  • 25. 25 @SvenRuppertThe way of working Start Learning again for example: functional add a new Language focus on a new paradigm but not everyone want to learn or better…. some are learning faster reactive this sometimes leads to ….. reactions….
  • 26. 26 @SvenRuppertThe way of working Start Learning again this sometimes leads to ….. reactions…. running away
  • 27. 27 @SvenRuppertThe way of working Start Learning again this sometimes leads to ….. reactions…. expecting something
  • 28. 28 @SvenRuppertThe way of working Start Learning again this sometimes leads to ….. reactions…. feeling the near end
  • 29. 29 @SvenRuppertThe way of working Start Learning again this sometimes leads to ….. reactions…. or only feeling to old
  • 30. 30 @SvenRuppertThe way of working Start Learning again this sometimes leads to ….. reactions…. you have to deal with this if you don´t want to loose them make them happy again How we solved this?
  • 31. prepare for Refactoring - Projectmanagement one size fit´s all ? 31 @SvenRuppert
  • 32. 32 @SvenRuppertThe way of working we are a product company with a lot of LTS contracts we created three streams Consultants - play and throw away Core Developers - collect and clean LTS Developers - keep alive Why ?
  • 33. 33 @SvenRuppertThe way of working Consultants - play and throw away Core Developer - collect and clean LTS Developer - keep alive Why ? some want to learn and experiment some need more stabil environments some did not want to change something
  • 34. 34 @SvenRuppertThe way of working Consultants - play and throw away Core Developer - collect and clean LTS Developer - keep alive Why ? some want to learn and experiment some need more stabil environments some did not want to change something amount of hours paid by the customer rated on hours the systems are stabil fixed income - bonus based on Change Request
  • 35. 35 @SvenRuppertThe way of working Consultants - play and throw away Core Developer - collect and clean LTS Developer - keep alive SCRUM Kanban customer driven roadmap driven
  • 36. 36 @SvenRuppertThe way of working SCRUM Kanban Consultants LTS - Developers Core - Developers Core - Developers Fire Consultants
  • 37. 37 @SvenRuppertThe way of working SCRUM Kanban Consultants LTS - Developers Core - Developers Consultants Consultants Consultants LTS - Developers LTS - Developers Core - Developers Core - Developers time based planning fixed size time slots version based dynamic size time slots
  • 38. prepare for Refactoring - Start learning again learn how to learn together with a team again 38 @SvenRuppert
  • 39. 39 @SvenRuppertKnowledge Sharing Consultants LTS - Developers Core - Developers build a source of knowledge
  • 40. 40 @SvenRuppertKnowledge Sharing Consultants LTS - Developers Core - Developers Hacking session Articles / Blogs Screencasts Refactoring Sessions POC
  • 41. 41 @SvenRuppertKnowledge Sharing How to motivate your team to do it ? explain it !!
  • 42. prepare for Refactoring - Technologies choose your weapons 42 @SvenRuppert
  • 43. 43 @SvenRuppertTechnical Migrations if you ask the consultants… to scale or change you need at least … ;-) NoSQL Events Akka / Scala Reactive Functional maybe ;-)
  • 44. 44 @SvenRuppertTechnical Transformation Swing Vaadin HashMap Hazelcast - Map JDBC - ResultSet Speedment - Streams what is the right technology for your team? what is the right order? Java OOP Java FRP
  • 45. 45 @SvenRuppertTechnical Transformation what is the right technology for your team? what is the right order? reduce complexity scale the team could work with a lot more…. start with new modules ? start with the oldest one ? most komplex one? … or ….
  • 46. 46 @SvenRuppertTechnical Transformation on thing that would limit your speed… time number of versions v1 v2 stabilize
  • 47. 47 @SvenRuppertTechnical Transformation on thing that would limit your speed… time number of versions v2 stabilize delta t compared to project lifetime
  • 48. prepare for Refactoring - Safety belt choose your weapons 48 @SvenRuppert
  • 49. 49 @SvenRuppertQM / QS - TDD Do you have bugs in your code ? since years you are working hard on this…. no
  • 50. 50 @SvenRuppertQM / QS - TDD Codebase is > 13 years old no test coverage how to decrease complexity? remember…. how to start? what is the right point to start? how to increase the quality of the tests?
  • 51. 51 TDD with jUnit @SvenRuppert are you using jUnit? assume that the following would make sense.. ;-) public class Service {
 public int add(int a, int b){
 if(a<2){
 return (a+b) * -1;
 } else {
 return a+b;
 }
 }
 } How many tests you will need ? it depends ;-)
  • 52. 52 TDD with jUnit @SvenRuppert public class Service {
 public int add(int a, int b){
 if(a<2){
 return (a+b) * -1;
 } else {
 return a+b;
 }
 }
 } How many tests you will need ? for line 100% coverage 2 but will this be enough? maybe ;-) how to find out, what will be enough? how to find the right tests? it depends ;-)
  • 53. 53 Mutation Testing @SvenRuppert generating the mutants and practical TDD with Mutation Testing running all junit tests check the reports write more / better tests loop until quality target reached
  • 54. 54 Mutation Testing - Hello World @SvenRuppert public class Service { public int add(int a, int b){ if (a<2) { return (a+b) * -1; } 
 else { return a+b; }
 }
 } 100% Line Coverage… and… @Test
 public void testAdd001() throws Exception {
 final int add = new Service().add(0, 0);
 Assertions.assertThat(add).isEqualTo(0);
 } @Test
 public void testAdd002() throws Exception {
 final int add = new Service().add(3, 0);
 Assertions.assertThat(add).isEqualTo(3);
 }
  • 55. 55 Mutation Testing - Hello World @SvenRuppert final int add = new Service().add(0, 0);
 Assertions.assertThat(add).isEqualTo(0); final int add = new Service().add(3, 0);
 Assertions.assertThat(add).isEqualTo(3);
  • 56. 56 Mutation Testing - Hello World @SvenRuppert final int add = new Service().add(0, 0); final int add = new Service().add(3, 0); >> Generated mutations Killed 3
  • 57. 57 Mutation Testing - Hello World @SvenRuppert final int add = new Service().add(0, 0); final int add = new Service().add(3, 0); >> Generated mutations Killed 3
  • 58. 58 Mutation Testing - in short words @SvenRuppert mutation testing is an add on to normal jUnit TDD tools are supporting it well generating and running all tests are time consuming but most important will effect your project structure
  • 59. 59 Mutation Testing - Lesson Learned @SvenRuppert mutation tests are often leading to …cleaner code compared to jUnit only
  • 60. 60 Mutation Testing - Lesson Learned @SvenRuppert public static final String[] discardCommonPrefix(String a, String b) { String[] ret = { a, b }; int l = a.length() < b.length() ? a.length() : b.length(); for (int i = 0; i < l; i++) { if (a.charAt(i) == b.charAt(i)) { if (i + 1 < l) { ret[0] = a.substring(i + 1); ret[1] = b.substring(i + 1); } else { if (a.length() < b.length()) { ret[0] = ""; ret[1] = b.substring(i + 1); } if (a.length() == b.length()) { ret[0] = ""; ret[1] = „"; } if (a.length() > b.length()) { ret[0] = a.substring(i + 1); ret[1] = „"; } } } else break; } return ret; }
  • 61. 61 Mutation Testing - Lesson Learned @SvenRuppert public String[] discardCommonPrefix(String a, String b) { final String[] ret = new String[2]; int l; if (a.length() < b.length()) { l = a.length(); } else { l = b.length(); } int position = 0; for (; position < l; position++) { final char charA = a.charAt(position); final char charB = b.charAt(position); if (charA != charB) { break; } } if (position >= a.length()) { ret[0] = ""; } else { ret[0] = a.substring(position); } if (position >= b.length()) { ret[1] = ""; } else { ret[1] = b.substring(position); } return ret; }
  • 62. 62 Mutation Testing - Lesson Learned @SvenRuppert Version 1 Version 2 for { if { if else { if if if } } else } if else for { if } if else if else
  • 63. 63 Example of useless Code @SvenRuppert
  • 68. prepare for Refactoring - Design Pattern start developing design pattern again 68 @SvenRuppert
  • 69. NestedBuilder - The Beginning 69 @SvenRuppert
  • 70. NestedBuilder - The Beginning 70 @SvenRuppert Car car = Car.newBuilder()
 .withEngine(engine)
 .withWheelList(wheels)
 .build(); Engine engine = Engine.newBuilder().withPower(100).withType(5).build(); Wheel wheel1 = Wheel.newBuilder().withType(2).withColour(3).withSize(4).build(); 
 Wheel wheel2 = Wheel.newBuilder().withType(2).withColour(3).withSize(4).build();
 Wheel wheel3 = Wheel.newBuilder().withType(2).withColour(3).withSize(4).build(); List<Wheel> wheels = new ArrayList<>();
 wheels.add(wheel1);
 wheels.add(wheel2);
 wheels.add(wheel3);}
  • 71. NestedBuilder - The Beginning 71 @SvenRuppert Car car = Car.newBuilder()
 .withEngine(engine)
 .withWheelList(wheels)
 .build(); Engine engine = Engine.newBuilder().withPower(100).withType(5).build(); Wheel wheel1 = Wheel.newBuilder().withType(2).withColour(3).withSize(4).build(); 
 Wheel wheel2 = Wheel.newBuilder().withType(2).withColour(3).withSize(4).build();
 Wheel wheel3 = Wheel.newBuilder().withType(2).withColour(3).withSize(4).build(); List<Wheel> wheels = new ArrayList<>();
 wheels.add(wheel1);
 wheels.add(wheel2);
 wheels.add(wheel3);
  • 72. NestedBuilder - The Beginning 72 @SvenRuppert Car car = Car.newBuilder()
 .withEngine(engine)
 .withWheelList(wheels)
 .build(); Engine engine = Engine.newBuilder().withPower(100).withType(5).build(); Wheel wheel1 = Wheel.newBuilder().withType(2).withColour(3).withSize(4).build(); 
 Wheel wheel2 = Wheel.newBuilder().withType(2).withColour(3).withSize(4).build();
 Wheel wheel3 = Wheel.newBuilder().withType(2).withColour(3).withSize(4).build(); //List<Wheel> wheels = new ArrayList<>();
 // wheels.add(wheel1);
 // wheels.add(wheel2);
 // wheels.add(wheel3); List<Wheel> wheelList = WheelListBuilder.newBuilder()
 .withNewList()
 .addWheel(wheel1)
 .addWheel(wheel2)
 .addWheel(wheel3)
 .build(); //more robust if you add tests at build() } } how to combine ? List<Wheel> wheels = new ArrayList<>();
 wheels.add(wheel1);
 wheels.add(wheel2);
 wheels.add(wheel3);
  • 73. NestedBuilder - The Beginning 73 @SvenRuppert Car car = Car.newBuilder()
 .withEngine(engine)
 .withWheelList(wheels)
 .build(); Engine engine = Engine.newBuilder().withPower(100).withType(5).build(); Wheel wheel1 = Wheel.newBuilder().withType(2).withColour(3).withSize(4).build(); 
 Wheel wheel2 = Wheel.newBuilder().withType(2).withColour(3).withSize(4).build();
 Wheel wheel3 = Wheel.newBuilder().withType(2).withColour(3).withSize(4).build(); List<Wheel> wheelList = WheelListBuilder.newBuilder()
 .withNewList()
 .addWheel(wheel1)
 .addWheel(wheel2)
 .addWheel(wheel3)
 .build(); } } how to combine ?
  • 74. NestedBuilder - The Beginning 74 @SvenRuppert Car car = Car.newBuilder()
 .withEngine(engine)
 .withWheelList(wheels)
 .build(); Engine engine = Engine.newBuilder().withPower(100).withType(5).build(); // Wheel wheel1 = Wheel.newBuilder().withType(2).withColour(3).withSize(4).build(); 
 // Wheel wheel2 = Wheel.newBuilder().withType(2).withColour(3).withSize(4).build();
 // Wheel wheel3 = Wheel.newBuilder().withType(2).withColour(3).withSize(4).build(); // List<Wheel> wheelList = WheelListBuilder.newBuilder()
 .withNewList()
 .addWheel(wheel1)
 .addWheel(wheel2)
 .addWheel(wheel3)
 .build(); List<Wheel> wheels = wheelListBuilder
 .addWheel().withType(1).withSize(2).withColour(2).addWheelToList()
 .addWheel().withType(1).withSize(2).withColour(2).addWheelToList()
 .addWheel().withType(1).withSize(2).withColour(2).addWheelToList()
 .addWheel().withType(1).withSize(2).withColour(2).addWheelToList()
 .build();
  • 75. NestedBuilder - The Beginning 75 @SvenRuppert Car car = Car.newBuilder()
 .withEngine(engine)
 .withWheelList(wheels)
 .build(); Engine engine = Engine.newBuilder().withPower(100).withType(5).build(); List<Wheel> wheels = wheelListBuilder
 .addWheel().withType(1).withSize(2).withColour(2).addWheelToList()
 .addWheel().withType(1).withSize(2).withColour(2).addWheelToList()
 .addWheel().withType(1).withSize(2).withColour(2).addWheelToList()
 .addWheel().withType(1).withSize(2).withColour(2).addWheelToList()
 .build(); WheelBuilder WheelListBuilder
  • 76. NestedBuilder - The Beginning 76 @SvenRuppert Car car = Car.newBuilder()
 .withEngine(engine)
 .withWheelList(wheels)
 .build(); Engine engine = Engine.newBuilder().withPower(100).withType(5).build(); List<Wheel> wheels = wheelListBuilder
 .addWheel().withType(1).withSize(2).withColour(2).addWheelToList()
 .addWheel().withType(1).withSize(2).withColour(2).addWheelToList()
 .addWheel().withType(1).withSize(2).withColour(2).addWheelToList()
 .addWheel().withType(1).withSize(2).withColour(2).addWheelToList()
 .build(); now we have to combine all Car car = Car.newBuilder()
 .addEngine().withPower(100).withType(5).done()
 .addWheels()
 .addWheel().withType(1).withSize(2).withColour(2).addWheelToList()
 .addWheel().withType(1).withSize(2).withColour(2).addWheelToList()
 .addWheel().withType(1).withSize(2).withColour(2).addWheelToList()
 .addWheel().withType(1).withSize(2).withColour(2).addWheelToList()
 .done()
 .build();
  • 77. NestedBuilder - The Pattern 77 @SvenRuppert public abstract class NestedBuilder<T, V> { protected T parent; public abstract V build() public <P extends NestedBuilder<T, V>> P 
 withParentBuilder(T parent) {
 this.parent = parent;
 return (P) this;
 } parent will connect itself…
  • 78. NestedBuilder - The Pattern 78 @SvenRuppert public abstract class NestedBuilder<T, V> { public T done() { Class<?> parentClass = parent.getClass(); try {
 V build = this.build();
 String methodname = "with" + build.getClass().getSimpleName();
 Method method = parentClass.getDeclaredMethod(
 methodname, build.getClass());
 method.invoke(parent, build);
 } catch (NoSuchMethodException 
 | IllegalAccessException | InvocationTargetException e) {
 e.printStackTrace();
 } } connect itself with parent
  • 79. NestedBuilder - The Pattern 79 @SvenRuppert the basic steps in short words the Parent-Builder will hold the Child-Builder the Parent-Builder will have a addChild - Method the Child-Builder will extend the NestedBuilder the rest could be generated with a 
 default Builder-Generator
  • 80. NestedBuilder - The Pattern 80 @SvenRuppert public class Parent {
 private KidA kidA;
 private KidB kidB;
 //snipp.....
 public static final class Builder {
 private KidA kidA;
 private KidB kidB;
 // to add manually
 private KidA.Builder builderKidA = KidA.newBuilder().withParentBuilder(this);
 private KidB.Builder builderKidB = KidB.newBuilder().withParentBuilder(this);
 
 public KidA.Builder addKidA() {
 return this.builderKidA;
 }
 public KidB.Builder addKidB() {
 return this.builderKidB;
 }
 //--------- connect itself with child switch to Child-Builder
  • 81. NestedBuilder - The Pattern 81 @SvenRuppert only extends on Child-Builder public static final class Builder 
 extends NestedBuilder<Parent.Builder, KidA> {
  • 82. NestedBuilder - The Pattern 82 @SvenRuppert Parent build = Parent.newBuilder()
 
 .addKidA().withNote("A").done()
 .addKidB().withNote("B").done()
 
 .build();
 System.out.println("build = " + build); and a child could be a parent in the same time Parent build = Parent.newBuilder()
 .addKidA().withNote("A") .addKidB().withNote("B").done() .done()
 .build(); System.out.println("build = " + build);

  • 83. Refactoring example based on Java8 @SvenRuppert
  • 84. 84 @SvenRuppertJava8 - Functional Interfaces - Example typical legacy implementation
  • 85. 85 @SvenRuppertJava8 - Functional Interfaces - Example typical legacy implementation
  • 86. 86 @SvenRuppertJava8 - Functional Interfaces - Example
  • 87. 87 @SvenRuppertJava8 - Functional Interfaces - Example
  • 88. 88 @SvenRuppertJava8 - Functional Interfaces - Example
  • 89. 89 @SvenRuppertJava8 - Functional Interfaces - Example
  • 90. 90 @SvenRuppertJava8 - Functional Interfaces - Example
  • 91. 91 @SvenRuppertJava8 - Functional Interfaces - Example Sourcecode is on github
  • 92. Interpreter - pre Java8 92 @SvenRuppert
  • 93. Interpreter - pre Java8 93 @SvenRuppert
  • 94. Interpreter - pre Java8 94 @SvenRuppert
  • 95. Interpreter - pre Java8 95 @SvenRuppert
  • 96. Interpreter - Java8 - Java9 96 @SvenRuppert
  • 97. Interpreter - Java8 - Java9 97 @SvenRuppert Main Idea - DataStructure to Function
  • 98. Memoizing partial cache-ing ? @SvenRuppert full example and code http://www.functional-reactive.org/
  • 99. prepare for Refactoring - Clean your code nano refactoring on language level 99 @SvenRuppert
  • 100. clean your code @SvenRuppert delete JavaDoc use final for Attributes as much as possible replace loops with streams extract Functional Interfaces remove anonymous classes use everywhere the same language level Why ?
  • 101. clean your code @SvenRuppert delete JavaDoc use final for Attributes as much as possible replace loops with streams extract Functional Interfaces remove anonymous classes use everywhere the same language level Why ? know the part you want to refactor homogeneous sources are better for machines
  • 102. prepare for Refactoring - Summary the full picture 102 @SvenRuppert
  • 103. Refactoring - Summary 103 @SvenRuppert prepare your team change the way of working work on your project management build your safety belt - mutation testing divide and conquer - @Inject build design pattern again extract cross functionality - Proxy's clean your code
  • 104. prepare for Management - Summary the full picture for the C-Level 104 @SvenRuppert
  • 105. Management - Summary 105 @SvenRuppert Now it is time to relax again ;-) Problem solved !
  • 106. Summary 106 @SvenRuppert places to read more about it www.functional-reactive.org www.java-9.org or contact me ;-) @SvenRuppert Thank You !!!