A method is Java's word for a reusable block of code — exactly what JavaScript and Python call a function. Up to now every line you've written has lived inside public static void main, which gets ugly fast: a single method that does everything is a method that does nothing well. Methods let you split a test framework into named, reusable pieces — loginAsAdmin(), validateResponse(...), formatDuration(...) — that you can call from anywhere. This lesson covers the shape of a method definition, how to call one, and the differences from JavaScript functions that catch beginners off guard.
The shape of a method
Every method has the same anatomy:
accessModifier returnType methodName(parameters) { body }
A real example:
public static String getGreeting(String name) {
return "Hello, " + name + "!";
}Read left to right:
public— the access modifier.publicmeans anyone can call it. Other options areprivate(only this class),protected(this class and subclasses), and the default (same package). For now, usepublic.static— belongs to the class itself rather than to an instance of the class. We'll come back to this in a moment.String— the return type. The method must give back aStringvalue. Usevoidif it returns nothing.getGreeting— the method name. Convention is camelCase starting with a verb:getGreeting,runTest,validateResponse. Names should describe an action.(String name)— the parameter list. Each parameter isType name. Multiple parameters are comma-separated.{ ... }— the method body. The code that runs when the method is called.return ...;— the value the caller receives. The expression's type must match the return type.
Calling a method
Calling a method runs its body and gives you back the return value:
public class Greeter {
public static String getGreeting(String name) {
return "Hello, " + name + "!";
}
public static void main(String[] args) {
String message = getGreeting("Alice");
System.out.println(message);
System.out.println(getGreeting("Bob"));
}
}Output:
Hello, Alice!
Hello, Bob!
The first call stores the return value in message. The second passes it straight to println. Both are valid uses of the same method.
void — methods that return nothing
When a method's job is to do something rather than compute a value, declare its return type as void:
public static void logResult(String message) {
System.out.println("[LOG] " + message);
}A void method has no return statement at the end (you can write a bare return; to exit early, but you don't have to). You call a void method as a statement on its own:
logResult("Login test passed"); // no value to capture
String x = logResult("..."); // ❌ compile error — can't store voidprintln, assertEquals, and most "do this thing" methods are void.
static — for now, treat it as required
You'll see static on every method in this chapter. Briefly:
- A static method belongs to the class. You call it with
ClassName.method(...)(or justmethod(...)from inside the same class). - An instance method belongs to an object — an instance of a class. You call it with
myObject.method(...).
Until chapter 4, when you'll start creating objects, every method you write should be static. That lets main (which is itself static) call them directly without needing an instance. Once we cover constructors and new, instance methods become the norm.
Methods with no parameters
If the method needs no input, the parameter list is just empty parentheses:
public static int getDefaultTimeout() {
return 5000;
}
public static void main(String[] args) {
int timeout = getDefaultTimeout();
System.out.println("Default timeout: " + timeout + "ms");
}Output:
Default timeout: 5000ms
Even when there are zero parameters, the parentheses are not optional — getDefaultTimeout (no parens) does not call the method, it's a method reference. We'll come back to those in chapter 8.
A real QA helper — validateResponse
The whole reason methods exist is to take a code shape that would otherwise be repeated across every test and pull it into one named place. A response validator is a perfect example:
public class ResponseHelpers {
public static boolean validateResponse(int statusCode, String body, long durationMs, long slaMs) {
if (statusCode < 200 || statusCode >= 300) return false;
if (body == null || body.isEmpty()) return false;
if (durationMs >= slaMs) return false;
return true;
}
public static void logResult(String testName, boolean passed) {
String label = passed ? "✅ PASS" : "❌ FAIL";
System.out.println(label + " " + testName);
}
public static void main(String[] args) {
boolean loginOk = validateResponse(200, "{\"id\":42}", 1450, 2000);
boolean searchOk = validateResponse(500, "", 800, 2000);
logResult("Login", loginOk);
logResult("Search", searchOk);
}
}Output:
✅ PASS Login
❌ FAIL Search
Read what the main method actually does: it makes two validateResponse calls, then logs each result. All the rules — status range, empty body, SLA — live in one named place. The day a fourth rule is added (e.g., must contain a specific header), you change validateResponse and every test that calls it picks up the new rule for free. That is the entire reason for methods.
The anatomy of a method, visualised
Five parts, always in the same order. Once you can read the parts left to right, every method you'll see in Selenium, TestNG, or Rest Assured documentation parses immediately.
Method naming — be a verb
Names matter because they're how future-you reads your test framework. Conventions every Java team follows:
- camelCase, starting with a lowercase letter:
validateResponse, notValidateResponse(PascalCase is for class names) and notvalidate_response(snake_case is for Python). - Start with a verb. Methods do things. Good:
calculatePassRate,findByTestId,loginAsAdmin. Less good:passRate,testId,admin— they read like nouns and tell the reader what the result is, not what the method does. get/setfor property-style accessors (you'll meet these in chapter 4):getStatusCode(),setBaseUrl(...).is/hasfor booleans:isLoggedIn(),hasErrors().- Be specific.
runTestis fine;loginTestis better;loginWithInvalidPasswordShouldFailis what a test method itself is named.
⚠️ Common mistakes
- Forgetting
static— and getting "non-static method cannot be referenced from a static context." This compile error happens whenmain(static) tries to call a method that isn't static. Until chapter 4, mark every helper methodstaticand the error goes away. Don't fix it by making fields static — that's the wrong direction. - Calling a method without parentheses.
getGreetingis a reference to the method;getGreeting("Alice")actually calls it. Beginners often writeString x = getGreeting;and get a confusing compile error. Always include the parens — even when the method takes zero arguments:getDefaultTimeout(). - Declaring a non-
voidreturn type and forgetting to return.public static int retries() { System.out.println("hi"); }won't compile — Java demands areturnalong every code path. The fix is either to addreturn 0;or change the type tovoid.
🎯 Practice task
Extract reusable test helpers. 25-30 minutes.
-
Create
TestHelpers.java. -
Define a method
public static String formatDuration(long ms)that returns a String like1.45sfor 1450 ms, or850msfor values under 1000. Hint:if (ms < 1000) return ms + "ms"; return (ms / 1000.0) + "s";. -
Define a method
public static double passRate(int passed, int total)that returns the pass rate as a percentage (e.g. 87.5 for 7 of 8). Use(double) passed / total * 100. -
Define a
voidmethodprintSummary(String suite, int passed, int failed, long durationMs)that prints three lines using the previous helpers. Sample output for"smoke",8,2,12450:Suite: smoke 8 passed, 2 failed (80.0%) Total time: 12.45s -
In
main, callprintSummarytwice with different inputs. Compile and run. -
Stretch: add a method
public static String label(boolean passed)that returns"✅ PASS"or"❌ FAIL". Replace the inline ternaries in your other methods with calls tolabel(...). Notice how a tiny extraction tightens every place that needs the same label.
You can now factor your code out of main. Lesson 2 expands on parameters and shows how Java handles multiple methods with the same name — a feature you'll use constantly in real test frameworks.