Your SlideShare is downloading. ×
Implementing Quality on Java projects
Upcoming SlideShare
Loading in...5
×

Thanks for flagging this SlideShare!

Oops! An error has occurred.

×

Saving this for later?

Get the SlideShare app to save on your phone or tablet. Read anywhere, anytime - even offline.

Text the download link to your phone

Standard text messaging rates apply

Implementing Quality on Java projects

10,890
views

Published on

Gives 5 hands on tips on how to improve a specific aspect of Quality on Java projects

Gives 5 hands on tips on how to improve a specific aspect of Quality on Java projects

Published in: Technology

2 Comments
8 Likes
Statistics
Notes
No Downloads
Views
Total Views
10,890
On Slideshare
0
From Embeds
0
Number of Embeds
14
Actions
Shares
0
Downloads
29
Comments
2
Likes
8
Embeds 0
No embeds

Report content
Flagged as inappropriate Flag as inappropriate
Flag as inappropriate

Select your reason for flagging this presentation as inappropriate.

Cancel
No notes for slide

Transcript

  • 1. Implementing Quality on Java projects Vincent Massol Committer XWiki XWiki SAS @vmassol 27 au 29 mars 2013Sunday, March 31, 13
  • 2. Vincent Massol • Speaker Bio • CTO XWiki SAS • Your Projects • XWiki (community-driven open source project) • Past: Maven, Apache Cargo, Apache Cactus, Pattern Testing • Other Credentials: • LesCastCodeurs podcast • Creator of OSSGTP open source group in Paris • 3 books: JUnit in Action, Maven: A Developer’s Notebook, BBWMSunday, March 31, 13
  • 3. What is Quality?Sunday, March 31, 13
  • 4. The XWiki project in summary • 9 years old • 28 active committers • 7 committers do 80% of work • 700K NCLOC • 11 commits/ day • 16 mails/daySunday, March 31, 13
  • 5. Examples of Quality actions • Coding rules (Checkstyle, ...) • Ensure API stability • Test coverage • Code reviews • Track bugs • License header checks • Don’t use Commons Lang 2.x • Release with Java 6 • Use SLF4J and don’t draw Log4J/ • Ensure javadoc exist JCL in dependencies • Prevent JAR hell • Automated build • Release often (every 2 weeks) • Automated unit tests • Collaborative design • Stable automated • Test on supported functional tests environments (DB & Browsers)Sunday, March 31, 13
  • 6. Quality Tip #1 API Stability 27 au 29 mars 2013Sunday, March 31, 13
  • 7. The Problem Class Not Found or Method Not FoundSunday, March 31, 13
  • 8. API Stability - Deprecations /** * ... * @deprecated since 2.4M1 use {@link #transform( * Block, TransformationContext)} */ @Deprecated void transform(XDOM dom, Syntax syntax) throws TransformationException;Sunday, March 31, 13
  • 9. API Stability - CLIRR (1/2) <plugin> <groupId>org.codehaus.mojo</groupId> <artifactId>clirr-maven-plugin</artifactId> <configuration> <ignored> <difference> <differenceType>7006</differenceType> <className>org/xwiki/.../MetaDataBlock</className> <method>org.xwiki....block.Block clone()</method> <to>org.xwiki.rendering.block.MetaDataBlock</to> <justification>XDOM#clone() doesnt clone the meta data</justification> </difference> ...Sunday, March 31, 13
  • 10. API Stability - CLIRR (2/2) Example from XWiki 5.0M1 Release notesSunday, March 31, 13
  • 11. API Stability - Internal Package Javadoc <plugin> <groupId>org.apache.maven.plugins</groupId> <artifactId>maven-javadoc-plugin <configuration> <excludePackageNames>*.internal.* </excludePackageNames> CLIRR <plugin> <groupId>org.codehaus.mojo</groupId> <artifactId>clirr-maven-plugin</artifactId> <excludes> <exclude>**/internal/**</exclude> <exclude>**/test/**</exclude>Sunday, March 31, 13
  • 12. API Stability - Legacy Module Aspect Weaving <plugin> <groupId>org.codehaus.mojo</groupId> <artifactId>aspectj-maven-plugin</...> ... <configuration> <weaveDependencies> <weaveDependency> <groupId>org.xwiki.rendering</...> <artifactId>xwiki-rendering-api</...> ... + “Legacy” ProfileSunday, March 31, 13
  • 13. API Stability - Young APIs /** * ... * @since 5.0M1 */ @Unstable(<optional explanation>) public EntityReference createEntityReference(String name,...) { ... } + max duration for keeping the annotation!Sunday, March 31, 13
  • 14. API Stability - Next steps • Annotation or package for SPI? • Better define when to use the @Unstable annotation • Not possible to add a new method to an existing Interface • Java 8 and Virtual Extension/Defender methods interface TestInterface {   public void testMe();   public void newMethod() default {     System.out.println("Default from interface");   } }Sunday, March 31, 13
  • 15. Quality Tip #2 JAR Hell 27 au 29 mars 2013Sunday, March 31, 13
  • 16. The Problem Class Not Found or Method Not Found or not working featureSunday, March 31, 13
  • 17. No duplicate classes @ runtime <plugin> <groupId>com.ning.maven.plugins</groupId> <artifactId>maven-duplicate-finder-plugin</artifactId> <executions> <execution> <phase>verify</phase> <goals> <goal>check</goal> </goals> <configuration> <failBuildInCaseOfConflict>true</...> <exceptions> ...Sunday, March 31, 13
  • 18. Surprising results... • Commons Beanutils bundles some classes from Commons Collections, apparently to avoid drawing a dependency to it... • Xalan bundles a lot of other projects (org/apache/xml/**, org/apache/ bcel/**, JLex/**, java_cup/**, org/apache/regexp/**). In addition, it even has these jars in its source tree without any indication about their versions... • stax-api, geronimo-stax-api_1.0_spec and xml-apis all draw javax.xml.stream.* classes • xmlbeans and xml-apis draw incompatible versions of org.w3c.dom.* classes 14 exceptions in total!Sunday, March 31, 13
  • 19. Maven: dependency version issue <dependencies> <dependency> Will run logback 0.9.9 <groupId>org.slf4j</groupId> with slf4J-api 1.4.0 <artifactId>slf4j-api</artifactId> instead of 1.5.0! <version>1.4.0</version> </dependency> <dependency> <groupId>ch.qos.logback</groupId> <artifactId>logback-classic</artifactId> <version>0.9.9</version> <!-- Depends on org.slf4j:slf4j-api:1.5.0 --> </dependency> </dependencies>Sunday, March 31, 13
  • 20. Maven: ensure correct version <plugin> <groupId>org.apache.maven.plugins</groupId> <artifactId>maven-enforcer-plugin</artifactId> <executions> <execution> <id>enforce-version-compatibility</id> <phase>verify</phase> <goals> <goal>enforce</goal> </goals> <configuration> <rules> <requireUpperBoundDeps/> </rules>Sunday, March 31, 13
  • 21. Quality Tip #3 Test Coverage 27 au 29 mars 2013Sunday, March 31, 13
  • 22. The Problem More bugs reported, overall quality goes down and harder to debug softwareSunday, March 31, 13
  • 23. Use Jacoco to fail the build <plugin> <groupId>org.jacoco</groupId> <artifactId>jacoco-maven-plugin</artifactId> <executions> <execution><id>jacoco-prepare</id> <goals><goal>prepare-agent</goal></goals> </execution> <execution><id>jacoco-check</id> <goals><goal>check</goal></goals> </execution> </executions> <configuration> <check> <instructionRatio>${xwiki.jacoco.instructionRatio}</...> </check>}Sunday, March 31, 13
  • 24. Strategy • When devs add code (and thus tests), increase the TPC percentage • Put the Jacoco check in “Quality” Maven Profile • Have a CI job to execute that profile regularly • About 15% overhead compared to build without checks • “Cheat mode”: Add easier-to-write testSunday, March 31, 13
  • 25. Quizz Time! Step 1: Building on my local machine gives the following: [INFO] --- jacoco-maven-plugin:0.6.2.201302030002:check (jacoco-check) [INFO] All coverage checks have been met. Step 2: Building on the CI machine gave: [INFO] --- jacoco-maven-plugin:0.6.2.201302030002:check (jacoco-check) [WARNING] Insufficient code coverage for INSTRUCTION: 75.52% < 75.53% Non determinism! Why?Sunday, March 31, 13
  • 26. Quizz Answer ... because the JVM is non deterministic! private Map componentEntries = new ConcurrentHashMap(); ... for (Map.Entry entry : componentEntries.entrySet()) { if (entry.getValue().instance == component) {   key = entry.getKey();     oldDescriptor = entry.getValue().descriptor;     break;   } }Sunday, March 31, 13
  • 27. Quality Tip #4 Functional Testing Stability (with Jenkins) 27 au 29 mars 2013Sunday, March 31, 13
  • 28. The Problem Too many false positives leading to developers not paying attention to CI emails anymore... leading to failing softwareSunday, March 31, 13
  • 29. False positives examples • The JVM has crashed • VNC is down (we run Selenium tests) • Browser crash (we run Selenium tests) • Git connection issue • Machine slowness (if XWiki cannot start under 2 minutes then it means the machine has some problems) • Nexus is down (we deploy our artifacts to a Nexus repository) • Connection issue (Read time out)Sunday, March 31, 13
  • 30. Step 1: Groovy PostBuild Plugin (1/2) def messages = [ [".*A fatal error has been detected by the Java Runtime Environment.*", "JVM Crash", "A JVM crash happened!"], [".*Error: cannot open display: :1.0.*", "VNC not running", "VNC connection issue!"], ... ] def shouldSendEmail = true messages.each { message -> if (manager.logContains(message.get(0))) { manager.addWarningBadge(message.get(1)) manager.createSummary("warning.gif").appendText(...) manager.buildUnstable() shouldSendEmail = false } }Sunday, March 31, 13
  • 31. Step 1: Groovy PostBuild Plugin (2/2) ... continued from previous slide... if (!shouldSendEmail) { def pa = new ParametersAction([ new BooleanParameterValue("noEmail", true) ]) manager.build.addAction(pa) }Sunday, March 31, 13
  • 32. Step 2: Mail Ext Plugin Pre-send Script import hudson.model.* build.actions.each { action -> if (action instanceof ParametersAction) { if (action.getParameter("noEmail")) { cancel = true } } }Sunday, March 31, 13
  • 33. Results + use the Scriptler plugin to automate configuration for all jobsSunday, March 31, 13
  • 34. Quality Tip #5 Bug Fixing Day 27 au 29 mars 2013Sunday, March 31, 13
  • 35. The Problem Bugs increasing, even simple to fix ones, devs focusing too much on new features (i.e. scope creep) vs fixing Bugs created vs closed what existsSunday, March 31, 13
  • 36. Bug Fixing Day • Every Thursday • Goal is to close the max number of bugs • Triaging: Can be closed with Won’t fix, Duplicate, Cannot Reproduce, etc • Close low hanging fruits in priority • Started with last 365 days then with last 547 days and currently with last 730 days (we need to catch up with 40 bugs!)Sunday, March 31, 13
  • 37. ResultsSunday, March 31, 13
  • 38. Conclusion 27 au 29 mars 2013Sunday, March 31, 13
  • 39. Parting words • Slowly add new quality check over time • Everyone must be on board • Favor Active Quality (i.e. make the build fail) over Passive checks • Be ready to adapt/remove checks if found not useful enough • Quality brings some risks: • Potentially less committers for your project (especially open source) • Project seen as “less fun”Sunday, March 31, 13
  • 40. Be proud of your Quality! “I have offended God and mankind because my work didnt reach the quality it should have.” Leonardo da Vinci, on his death bedSunday, March 31, 13