Testng: 슈퍼 클래슀의 @Test λ©”μ†Œλ“œλŠ” λͺ¨λ“  μ„œλΈŒ ν΄λž˜μŠ€μ— λŒ€ν•΄ λ‹€μ‹œ μ‹€ν–‰λ©λ‹ˆλ‹€.

에 λ§Œλ“  2019λ…„ 06μ›” 10일  Β·  12μ½”λ©˜νŠΈ  Β·  좜처: cbeust/testng

TestNG 버전 6.14.3

μ˜ˆμƒλ˜λŠ” 행동

μƒμœ„ 클래슀의 @Test λ©”μ†Œλ“œλŠ” μƒμœ„ 클래슀λ₯Ό μƒμ†ν•˜λŠ” ν•˜μœ„ 클래슀의 μˆ˜μ— 관계없이 ν•œ 번만 μ‹€ν–‰λ©λ‹ˆλ‹€.

μ‹€μ œ 행동

@Test λ©”μ„œλ“œλŠ” 각 ν•˜μœ„ ν΄λž˜μŠ€μ™€ ν•¨κ»˜ μ‹€ν–‰λ©λ‹ˆλ‹€.

λŸ¬λ„ˆμ—μ„œ 문제λ₯Ό μž¬ν˜„ν•  수 μžˆμŠ΅λ‹ˆκΉŒ?

  • [ ] 껍데기
  • [ ] 메이븐
  • [x] κ·Έλž˜λ“€
  • [ ] 개미
  • [ ] 이클립슀
  • [ ] μΈν…”λ¦¬μ œμ΄
  • [ ] λ„·λΉˆ

ν…ŒμŠ€νŠΈ μΌ€μ΄μŠ€ μƒ˜ν”Œ

public class BaseTest  extends SetupClass{
    @BeforeClass...
    @BeforeMethod...
    @AfterClass...
    @AfterMethod....

    <strong i="22">@Test</strong>
    public void baseMethod(){
        System.out.println("base method");
    }
}
public class Test1 extends BaseTest{
    <strong i="25">@Test</strong>
    public void test1(){
        System.out.println("test1");
    }
}
public class Test2 extends BaseTest{
    <strong i="28">@Test</strong>
    public void test2(){
        System.out.println("test2");
    }
}

λ‹€μŒκ³Ό 같은 TestNG xml νŒŒμΌμ—μ„œ μ΄λŸ¬ν•œ ν…ŒμŠ€νŠΈλ₯Ό λ³‘λ ¬λ‘œ μ‹€ν–‰ν•˜κ³  μžˆμŠ΅λ‹ˆλ‹€.

<suite name="Regression Suite" verbose="1" parallel="classes" thread-count="4">
    <parameter name="project" value="TestPrj"/>
    <parameter name="server" value="QA01"/>
    <test name="QA01 TestPrj">
        <parameter name="environment" value="macos"/>
        <groups>
            <run>
                <include name="regression"/>
            </run>
        </groups>
        <packages>
            <package name="test"/>
        </packages>
    </test>
</suite>

μΆ”μ‹  github λ¬Έμ œμ—μ„œ μ½”λ“œλ₯Ό νŽΈμ§‘ν•˜λŠ” 것은 맀우 λ‚˜μ©λ‹ˆλ‹€... λ‹€λ₯Έ κ²ƒμœΌλ‘œ μ΄λ™ν•˜μ‹­μ‹œμ˜€.

inheritance

λͺ¨λ“  12 λŒ“κΈ€

@vlad230

μΆ”μ‹  github λ¬Έμ œμ—μ„œ μ½”λ“œλ₯Ό νŽΈμ§‘ν•˜λŠ” 것은 맀우 λ‚˜μ©λ‹ˆλ‹€... λ‹€λ₯Έ κ²ƒμœΌλ‘œ μ΄λ™ν•˜μ‹­μ‹œμ˜€.

Markdown에 μ΅μˆ™ν•΄μ§€λŠ” 데 μ‹œκ°„μ„ ν• μ• ν•  수 μžˆμŠ΅λ‹ˆλ‹€. μ΄λ ‡κ²Œ ν•˜λ©΄ μ„œμ‹ 지정과 ν•¨κ»˜ μ½”λ“œ 쑰각을 맀우 μ‰½κ²Œ μΆ”κ°€ν•  수 μžˆμŠ΅λ‹ˆλ‹€.

μ—¬κΈ°μ—μ„œ κ·€ν•˜μ˜ 문제λ₯Ό μ΄ν•΄ν•˜κ³  μžˆλŠ”μ§€ 잘 λͺ¨λ₯΄κ² μŠ΅λ‹ˆλ‹€. ꢁ극적으둜 μžμ‹ ν΄λž˜μŠ€λŠ” κΈ°λ³Έ 클래슀 λ©”μ„œλ“œλ„ κ°€μ Έμ˜΅λ‹ˆλ‹€. 그리고 TestNG μ£Όμ„μœΌλ‘œ 주석이 달린 경우 λͺ¨λ“  ν•˜μœ„ ν΄λž˜μŠ€μ— λŒ€ν•΄ μ‹€ν–‰λ©λ‹ˆλ‹€. 이것이 TestNG의 λ™μž‘μž…λ‹ˆλ‹€. λ”°λΌμ„œ TestNGκ°€ μ„€κ³„λœ λŒ€λ‘œ μž‘λ™ν•˜κ³  μžˆλ‹€κ³  λ§ν•˜κ³  μ‹ΆμŠ΅λ‹ˆλ‹€.

@juherr - λ‹Ήμ‹ μ˜ 생각은?

@krmahadevan 포맷

μ—¬κΈ°μ—μ„œ κ·€ν•˜μ˜ 문제λ₯Ό μ΄ν•΄ν•˜κ³  μžˆλŠ”μ§€ 잘 λͺ¨λ₯΄κ² μŠ΅λ‹ˆλ‹€. ꢁ극적으둜 μžμ‹ ν΄λž˜μŠ€λŠ” κΈ°λ³Έ 클래슀 λ©”μ„œλ“œλ„ κ°€μ Έμ˜΅λ‹ˆλ‹€. 그리고 TestNG μ£Όμ„μœΌλ‘œ 주석이 달린 경우 λͺ¨λ“  ν•˜μœ„ ν΄λž˜μŠ€μ— λŒ€ν•΄ μ‹€ν–‰λ©λ‹ˆλ‹€. 이것이 TestNG의 λ™μž‘μž…λ‹ˆλ‹€. λ”°λΌμ„œ TestNGκ°€ μ„€κ³„λœ λŒ€λ‘œ μž‘λ™ν•˜κ³  μžˆλ‹€κ³  λ§ν•˜κ³  μ‹ΆμŠ΅λ‹ˆλ‹€.

당신이 λ‚˜μ—κ²Œ λ¬»λŠ”λ‹€λ©΄, 슈퍼 ν΄λž˜μŠ€μ—μ„œ ν…ŒμŠ€νŠΈλ₯Ό μ—¬λŸ¬ 번 μ‹€ν–‰ν•˜λŠ” 것은 μ˜λ―Έκ°€ μ—†μŠ΅λ‹ˆλ‹€.
이것이 μ§€κΈˆ TestNG의 μ˜ˆμƒλ˜λŠ” λ™μž‘μ΄λΌλ©΄ κ°œμ„ μœΌλ‘œ μΆ”κ°€ν•  수 μžˆμŠ΅λ‹ˆλ‹€.

μ„€κ³„λœ λŒ€λ‘œ μž‘λ™ν•©λ‹ˆλ‹€.
자체 ν΄λž˜μŠ€μ—μ„œ baseMethod ν…ŒμŠ€νŠΈλ₯Ό μ΄λ™ν•˜μ§€ μ•ŠλŠ” μ΄μœ λŠ” λ¬΄μ—‡μž…λ‹ˆκΉŒ?

@vlad230

당신이 λ‚˜μ—κ²Œ λ¬»λŠ”λ‹€λ©΄, 슈퍼 ν΄λž˜μŠ€μ—μ„œ ν…ŒμŠ€νŠΈλ₯Ό μ—¬λŸ¬ 번 μ‹€ν–‰ν•˜λŠ” 것은 μ˜λ―Έκ°€ μ—†μŠ΅λ‹ˆλ‹€.

μ •ν™•νžˆ 무엇을 λ‹¬μ„±ν•˜λ €κ³  ν•©λ‹ˆκΉŒ? μ‹œλ‚˜λ¦¬μ˜€λ₯Ό μžμ„Ένžˆ μ„€λͺ…ν•˜κ±°λ‚˜ μ„€λͺ…ν•˜λŠ” 데 도움이 λœλ‹€λ©΄ 쒋을 κ²ƒμž…λ‹ˆλ‹€.

이것이 μ§€κΈˆ TestNG의 μ˜ˆμƒλ˜λŠ” λ™μž‘μ΄λΌλ©΄ κ°œμ„ μœΌλ‘œ μΆ”κ°€ν•  수 μžˆμŠ΅λ‹ˆλ‹€.

반 직관적이기 λ•Œλ¬Έμ— κ°œμ„  μ‚¬ν•­μœΌλ‘œ λ°›μ•„λ“€μ—¬μ§ˆμ§€ 확신이 μ„œμ§€ μ•ŠμŠ΅λ‹ˆλ‹€. κΈ°λ³Έ 클래슀 λ©”μ„œλ“œκ°€ μ–Όλ§ˆλ‚˜ λ§Žμ€ μžμ‹ ν΄λž˜μŠ€κ°€ μžˆλŠ”μ§€μ— 관계없이 기본적으둜 μ •ν™•νžˆ ν•œ 번만 μ‹€ν–‰λ˜κΈ°λ₯Ό μ›ν•œλ‹€λ©΄ λ‹€μŒμ„ μˆ˜ν–‰ν•˜μ—¬ 였늘 ν…ŒμŠ€νŠΈ ν”„λ‘œμ νŠΈμ—μ„œ μˆ˜ν–‰ν•  수 μžˆμŠ΅λ‹ˆλ‹€.

  1. κΈ°λ³Έ ν΄λž˜μŠ€μ—μ„œ org.testng.IHookable κ΅¬ν˜„
  2. run() λ©”μ„œλ“œ λ‚΄μ—μ„œ κΈ°λ³Έ 클래슀 λ©”μ„œλ“œκ°€ 이미 μ‹€ν–‰λ˜μ—ˆλŠ”μ§€ ν™•μΈν•˜κ³  μ‹€ν–‰λ˜μ§€ μ•Šμ€ 경우 μ‹€ν–‰ν•˜λŠ” νŽΈμ§‘ 검사λ₯Ό μΆ”κ°€ν•©λ‹ˆλ‹€.

μ—¬κΈ° μƒ˜ν”Œμ΄ μžˆμŠ΅λ‹ˆλ‹€

κΈ°λ³Έ 클래슀 λ©”μ„œλ“œκ°€ ν•œ 번만 μ‹€ν–‰λ˜μ–΄μ•Ό 함을 λ‚˜νƒ€λ‚΄λŠ” 마컀 μΈν„°νŽ˜μ΄μŠ€

import static java.lang.annotation.ElementType.METHOD;
import static java.lang.annotation.ElementType.TYPE;

import java.lang.annotation.Retention;
import java.lang.annotation.Target;

@Retention(java.lang.annotation.RetentionPolicy.RUNTIME)
@Target({METHOD, TYPE})
public <strong i="20">@interface</strong> RunOnce {
}

λ‹€μŒμ€ μƒνƒœ 좔적기 μ‹±κΈ€ν†€μž…λ‹ˆλ‹€.

import java.lang.reflect.Method;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;

public class StateTracker {

  private static final StateTracker instance = new StateTracker();

  private final Map<String, Object> runOnceData = new ConcurrentHashMap<>();

  private StateTracker() {}

  public static StateTracker getInstance() {
    return instance;
  }

  boolean canExecute(Method method) {
    RunOnce runOnce = method.getAnnotation(RunOnce.class);
    String methodName = method.getName();
    boolean execute = true;
    if (runOnce != null) {
      if (runOnceData.containsKey(methodName)) {
        execute = false;
      } else {
        runOnceData.put(methodName, new Object());
      }
    }
    return execute;
  }
}

κΈ°λ³Έ ν΄λž˜μŠ€λŠ” λ‹€μŒκ³Ό κ°™μŠ΅λ‹ˆλ‹€.

import org.testng.IHookCallBack;
import org.testng.IHookable;
import org.testng.ITestResult;
import org.testng.annotations.Test;

public class BaseTest implements IHookable {

  <strong i="27">@Test</strong>
  <strong i="28">@RunOnce</strong>
  public void baseclassTestMethod() {
    System.err.println("Base class test method executed");
  }

  <strong i="29">@Override</strong>
  public void run(IHookCallBack callBack, ITestResult testResult) {
    boolean execute =
        StateTracker.getInstance()
            .canExecute(testResult.getMethod().getConstructorOrMethod().getMethod());
    if (execute) {
      callBack.runTestMethod(testResult);
    } else {
      testResult.setStatus(ITestResult.SKIP);
      testResult.setThrowable(new RuntimeException("Intentionally skipping"));
    }
  }
}

ν•˜μœ„ ν΄λž˜μŠ€λŠ” λ‹€μŒκ³Ό κ°™μŠ΅λ‹ˆλ‹€.

import org.testng.annotations.Test;

public class ChildClass1 extends BaseTest {

  <strong i="33">@Test</strong>
  public void childTest() {
    System.err.println(getClass().getName() + ".childTest() executed");
  }
}
import org.testng.annotations.Test;

public class ChildClass2 extends BaseTest {

  <strong i="36">@Test</strong>
  public void childTest() {
    System.err.println(getClass().getName() + ".childTest() executed");
  }
}

ν…ŒμŠ€νŠΈ κ²°κ³Όλ₯Ό μ •λ¦¬ν•˜κ³  @RunOnce μ‚¬μš©ν•˜μ—¬ 주석이 달린 κ±΄λ„ˆλ›΄ ν…ŒμŠ€νŠΈλ₯Ό μ œκ±°ν•˜λŠ” 필터링 λ©”μ»€λ‹ˆμ¦˜μ„ μΆ”κ°€ν•΄μ•Ό ν•©λ‹ˆλ‹€.

@krmahadevan
μ •ν™•νžˆ 무엇을 λ‹¬μ„±ν•˜λ €κ³  ν•©λ‹ˆκΉŒ? μ‹œλ‚˜λ¦¬μ˜€λ₯Ό μžμ„Ένžˆ μ„€λͺ…ν•˜κ±°λ‚˜ μ„€λͺ…ν•˜λŠ” 데 도움이 λœλ‹€λ©΄ 쒋을 κ²ƒμž…λ‹ˆλ‹€.

μ—¬λŸ¬ 클래슀(κΈ°λŠ₯κ³Ό κ΄€λ ¨λœ)μ—μ„œ ν…ŒμŠ€νŠΈλ₯Ό λΆ„λ¦¬ν•˜λ €κ³  ν•©λ‹ˆλ‹€. 예λ₯Ό λ“€μ–΄, 당신은 츑면을 따라 κΈ°λ³Έ ν΄λž˜μŠ€μ—μ„œ ν…ŒμŠ€νŠΈλ₯Ό 지원 μΈ‘λ©΄ λ‹€λ₯Έ λ„μš°λ―Έ λ©”μ„œλ“œλ₯Ό 따라 @Before 및 @After 방법 (μ•ˆ ν…ŒμŠ€νŠΈ)에 ν•΄λ‹Ή κΈ°λŠ₯에 λŒ€ν•œ μ„€μ • λΆ€λΆ„μ΄μžˆλŠ” "κΈ°λ³Έ 클래슀"λ₯Ό 가지고 "μžμ‹ ν΄λž˜μŠ€μ—μ„œ ν…ŒμŠ€νŠΈ ". λ”°λΌμ„œ 이 λ°©λ²•μœΌλ‘œ μžμ‹ ν΄λž˜μŠ€μ— μƒˆ ν…ŒμŠ€νŠΈλ₯Ό μΆ”κ°€ν•˜κ³  μžμ‹ 클래슀의 μ½”λ“œλ₯Ό λ³΅μ œν•˜μ§€ μ•ŠμŠ΅λ‹ˆλ‹€.
κΈ°λ³Έ ν΄λž˜μŠ€μ—λŠ” ν•΄λ‹Ή κΈ°λŠ₯의 보닀 일반적인 뢀뢄을 ν…ŒμŠ€νŠΈν•˜λŠ” λͺ‡ 가지 ν…ŒμŠ€νŠΈ λ©”μ„œλ“œκ°€ 있고 μžμ‹ ν΄λž˜μŠ€μ—λŠ” 보닀 ꡬ체적인 ν…ŒμŠ€νŠΈκ°€ μžˆμŠ΅λ‹ˆλ‹€.
클래슀λ₯Ό λ³‘λ ¬λ‘œ μ‹€ν–‰ν•˜μ—¬ ν…ŒμŠ€νŠΈ μ‹€ν–‰ μ‹œκ°„μ„ μ΅œμ ν™”ν•˜λ €κ³  ν•˜κΈ° λ•Œλ¬Έμ— 50개 μ΄μƒμ˜ ν…ŒμŠ€νŠΈ λ©”μ„œλ“œκ°€ μžˆλŠ” μ›λž˜ "κΈ°λ³Έ 클래슀"λ₯Ό μ—¬λŸ¬ 개의 더 μž‘μ€ "μžμ‹ 클래슀"둜 λΆ„ν• ν•˜μ—¬ μ΄λŸ¬ν•œ 더 μž‘μ€ ν΄λž˜μŠ€κ°€ λ‹€λ₯Έ μŠ€λ ˆλ“œμ— λ°°ν¬λ˜λ„λ‘ ν•΄μ•Ό ν–ˆμŠ΅λ‹ˆλ‹€. /μ‹€ν–‰μž.

@krmahadevan 은 μžμ„Έν•œ μ†”λ£¨μ…˜μ— λŒ€ν•΄
κΈ°λ³Έ ν΄λž˜μŠ€μ—μ„œ ν…ŒμŠ€νŠΈλ₯Ό μ§€μ†μ μœΌλ‘œ λ‹€μ‹œ μ‹€ν–‰ν•  ν•„μš”κ°€ μ—†μŠ΅λ‹ˆλ‹€. μ„€μ •/ν•΄μ œ 문제인 경우 항상 @Before/ @After λ₯Ό μ‚¬μš©ν•  수 있으며 κΈ°λ³Έ 클래슀의 μžμ‹ 클래슀 이전에 맀번 λ‹€μ‹œ μ‹€ν–‰λ©λ‹ˆλ‹€.

예, λ™μž‘μ„ ꡬ성할 수 μžˆλ‹€κ³  μƒκ°ν•©λ‹ˆλ‹€.

사싀, 각 μžμ‹ μΈμŠ€ν„΄μŠ€μ— λŒ€ν•΄ λΆ€λͺ¨ ν…ŒμŠ€νŠΈλ₯Ό μ‹€ν–‰ν•˜λ €λŠ” μ‚¬μš© 사둀λ₯Ό 찾지 λͺ»ν–ˆμŠ΅λ‹ˆλ‹€.
ν…ŒμŠ€νŠΈ μƒνƒœκ°€ 톡합 ν…ŒμŠ€νŠΈμ—μ„œ 자주 μˆ˜μ •λ˜κΈ° λ•Œλ¬Έμ— ν…ŒμŠ€νŠΈ( dependsOnMethods )에 λŒ€ν•œ 직접적인 쒅속성이 μ—†λŠ” ν•œ.

@krmahadevan WDYT?

@vlad230

μžμ„Έν•œ μ†”λ£¨μ…˜μ— λŒ€ν•΄ λŒ€λ‹¨νžˆ κ°μ‚¬ν•˜μ§€λ§Œ λ‚˜μ—κ²Œ 쑰금 번거둭게 λ³΄μž…λ‹ˆλ‹€

κ·€ν•˜μ˜ μ‚¬μš© 사둀도 일반 것과 μ•½κ°„ λ‹€λ₯΄κ²Œ λ³΄μž…λ‹ˆλ‹€. λ”μš±μ΄ λ‚˜λŠ” 그것이 μ–΄λ–»κ²Œ μ΄λ£¨μ–΄μ§ˆ 수 μžˆλŠ”μ§€μ— λŒ€ν•œ μ‹€μ œ 예λ₯Ό μ œμ‹œν–ˆμŠ΅λ‹ˆλ‹€. 당신이해야 ν•  일은 이것을 μ±„νƒν•˜κ³  이것을 κΈ°λ°˜μœΌλ‘œν•˜λŠ” κ²ƒμž…λ‹ˆλ‹€.

TestNGλŠ” μ‚¬μš©μž μ •μ˜ν•  수 μžˆμœΌλ―€λ‘œ κΈ°λ³Έ λ™μž‘μœΌλ‘œ 보고 μ‹ΆμŠ΅λ‹ˆλ‹€.

μ•„λ‹ˆμš”. 제 μƒκ°μ—λŠ” κ·Έλ ‡κ²Œ ν•  수 μ—†μŠ΅λ‹ˆλ‹€. ν…ŒμŠ€νŠΈλŠ” 항상 μ‹€ν–‰λ˜μ–΄μ•Ό ν•©λ‹ˆλ‹€. κΈ°λ³Έ ν΄λž˜μŠ€μ— μžˆλ‹€κ³  ν•΄μ„œ μ„ νƒμ μœΌλ‘œ μ‹€ν–‰ν•΄μ•Ό ν•˜λŠ” 것은 μ•„λ‹™λ‹ˆλ‹€. TestNGλŠ” μ‚¬μš©μž μ •μ˜ν•  수 μžˆμŠ΅λ‹ˆλ‹€. κ·ΈλŸ¬λ‚˜ 이것이 TestNGκ°€ λͺ¨λ“  μ‚¬μš©μž μ •μ˜λ₯Ό 지원해야 ν•œλ‹€λŠ” 것을 μ˜λ―Έν•˜μ§€λŠ” μ•ŠμŠ΅λ‹ˆλ‹€. μ‚¬μš©μžκ°€ ν•„μš”μ— 맞게 μ‚¬μš©μž μ •μ˜ν•˜κ³  μž‘μ—…ν•  수 μžˆλŠ” 방법을 μ œκ³΅ν•˜κΈ°λ§Œ ν•˜λ©΄ λ©λ‹ˆλ‹€. λ‚΄κ°€ κ³΅μœ ν•œ μƒ˜ν”Œμ€ TestNGλ₯Ό λ³€κ²½ν•  ν•„μš” 없이 μ΄λŸ¬ν•œ μ‚¬μš©μž μ •μ˜λ₯Ό μ μš©ν•œ μ˜ˆμž…λ‹ˆλ‹€.

κΈ°λ³Έ ν΄λž˜μŠ€μ—μ„œ ν…ŒμŠ€νŠΈλ₯Ό μ§€μ†μ μœΌλ‘œ λ‹€μ‹œ μ‹€ν–‰ν•  ν•„μš”κ°€ μ—†μŠ΅λ‹ˆλ‹€. μ„€μ •/ν•΄μ œ 문제인 경우 항상 @Before/ @after λ₯Ό μ‚¬μš©ν•  수 있으며 κΈ°λ³Έ 클래슀의 μžμ‹ 클래슀 이전에 맀번 λ‹€μ‹œ μ‹€ν–‰λ©λ‹ˆλ‹€.

λ‚˜μ—κ²Œ 그것은 사물을 λ³΄λŠ” ν•œ 가지 방법일 λΏμž…λ‹ˆλ‹€. νŠΉμ • λ©”μ†Œλ“œκ°€ 맀번 μ‹€ν–‰λ˜μ§€ μ•Šμ•„μ•Ό ν•œλ‹€λ©΄ @Test 주석을 μ‚¬μš©ν•˜μ§€ μ•Šμ•„μ•Ό ν•©λ‹ˆλ‹€. @BeforeTest ( <test> νƒœκ·Έλ‹Ή ν•œ 번만 싀행됨) λ˜λŠ” @BeforeSuite ( <suite> λ‹Ή ν•œ 번만 싀행됨)와 같은 ꡬ성 주석을 맀우 잘 μ‚¬μš©ν•  수 μžˆμŠ΅λ‹ˆλ‹€

κΈ°λ³Έ 클래슀의 ν…ŒμŠ€νŠΈ λ©”μ„œλ“œκ°€ μ‹€μ œλ‘œ ν…ŒμŠ€νŠΈ λ©”μ„œλ“œμΈμ§€ ν™•μ‹€ν•˜μ§€ μ•ŠμŠ΅λ‹ˆλ‹€. λ‚˜μ—κ²Œ 그것듀은 ν…ŒμŠ€νŠΈκ°€ μ‹€ν–‰λ˜κΈ° μœ„ν•΄ 좩쑱될 μ„€μ • 쑰건을 μ„€μ •ν•˜λŠ” κ΅¬μ„±μ²˜λŸΌ λ“€λ¦½λ‹ˆλ‹€.

@juherr - μ—¬κΈ°μ˜ μ‚¬μš© 사둀에 λ™μ˜ν•˜λŠ”μ§€ 잘 λͺ¨λ₯΄κ² μŠ΅λ‹ˆλ‹€. 발견된 μœ„μΉ˜μ— 관계없이 ν…ŒμŠ€νŠΈλ₯Ό μ‹€ν–‰ν•΄μ•Ό ν•©λ‹ˆλ‹€. λͺ¨λ“  μžμ‹ ν΄λž˜μŠ€μ— λŒ€ν•΄ μ‹€ν–‰λ˜λŠ” 것을 μ›ν•˜μ§€ μ•ŠλŠ” μ‹œλ‚˜λ¦¬μ˜€κ°€ μžˆλŠ” 경우 @Test 주석이 μ•„λ‹Œ ꡬ성 주석을 μ‚¬μš©ν•΄μ•Ό ν•©λ‹ˆλ‹€.

κ΅¬ν˜„ μΈ‘λ©΄μ—μ„œ, 특히 μ‚¬λžŒλ“€μ΄ μ‹€ν–‰ μˆ˜λ‹¨μœΌλ‘œ 그룹을 μ‚¬μš©ν•˜κΈ° μ‹œμž‘ν•  λ•Œ μ½”λ“œλ² μ΄μŠ€μ— λ§Žμ€ ν˜Όλž€μ΄ 좔가될 것이라고 μƒκ°ν•©λ‹ˆλ‹€.

λ˜ν•œ ν˜„μž¬ TestNG λ‚΄μ—μ„œ 이미 이 μž‘μ—…μ„ μˆ˜ν–‰ν•  수 μžˆλŠ” 방법이 μžˆλ‹€κ³  μƒκ°ν•©λ‹ˆλ‹€(예둜 κ³΅μœ ν–ˆμŠ΅λ‹ˆλ‹€). μ™œ 그것을 ν™œμš©ν•˜μ§€ μ•ŠμŠ΅λ‹ˆκΉŒ? 이것은 μΌνšŒμ„± μ‚¬μš© μ‚¬λ‘€λ‘œ 보이며 TestNGκ°€ μ‚¬μš©λ˜λŠ” 일반적인 방식에 λ§žμ§€ μ•ŠλŠ” 것 κ°™μŠ΅λ‹ˆλ‹€.

@krmahadevan μ£„μ†‘ν•©λ‹ˆλ‹€λ§Œ μ œκ°€ ν•˜λ €λŠ” 것을 μ΄ν•΄ν•˜μ§€ κ°™μŠ΅λ‹ˆλ‹€ .
λ‚΄ μƒμœ„ 클래슀(BaseTest - 예: DashboardTest)μ—λŠ” ν˜„μž¬ 15개의 ν…ŒμŠ€νŠΈκ°€ 있고 각각 내뢀에 ν…ŒμŠ€νŠΈκ°€ μžˆλŠ” 3개의 ν•˜μœ„ 클래슀(예: DashboardFilterTest, DashboardTreeTest, DashboardEditorTest)κ°€ μžˆμŠ΅λ‹ˆλ‹€. λ‚΄ κ²Œμ‹œλ¬Όμ—μ„œ μ„€λͺ…ν•œ μ ‘κ·Ό 방식을 μ‚¬μš©ν•˜μ—¬ ν…ŒμŠ€νŠΈλ₯Ό μ‹€ν–‰ν•  λ•Œλ§ˆλ‹€ ν•΄λ‹Ή 15개의 ν…ŒμŠ€νŠΈκ°€ 3번 이상 μ‹€ν–‰λ©λ‹ˆλ‹€(즉, 3x15 = 45개의 ν…ŒμŠ€νŠΈκ°€ 싀행됨). 15번 ν…ŒμŠ€νŠΈ.

λ‚˜λŠ” μ—¬μ „νžˆ λΆ€λͺ¨ ν΄λž˜μŠ€μ— μžˆλŠ” ν…ŒμŠ€νŠΈκ°€ μžμ‹ ν΄λž˜μŠ€μ—μ„œ ν…ŒμŠ€νŠΈκ°€ 싀행될 λ•Œλ§ˆλ‹€ λ‹€μ‹œ μ‹€ν–‰λ˜λŠ” 것은 말이 λ˜μ§€ μ•ŠλŠ”λ‹€κ³  μƒκ°ν•©λ‹ˆλ‹€. TestNG의 κΈ°λ³Έ λ™μž‘μ€ 그것을 ν™•μž₯ν•˜λŠ” μžμ‹ 클래슀의 μˆ˜μ— 관계없이 λΆ€λͺ¨ ν΄λž˜μŠ€μ—μ„œ ν…ŒμŠ€νŠΈ λ©”μ„œλ“œλ₯Ό ν•œ 번 μ‹€ν–‰ν•˜λŠ” 것을 μ„ ν˜Έν•©λ‹ˆλ‹€.

이것이 λΆˆκ°€λŠ₯ν•˜λ‹€λ©΄ μ΄ν•΄ν•©λ‹ˆλ‹€. μ–΄μ¨Œλ“  κ°μ‚¬ν•©λ‹ˆλ‹€.

@vlad230

μΆ”κ°€ μ»¨ν…μŠ€νŠΈλ₯Ό μΆ”κ°€ν•΄ μ£Όμ…”μ„œ κ°μ‚¬ν•©λ‹ˆλ‹€.

λ‚΄ μƒμœ„ 클래슀(BaseTest - 예: DashboardTest)μ—λŠ” ν˜„μž¬ 15개의 ν…ŒμŠ€νŠΈκ°€ 있고 각각 내뢀에 ν…ŒμŠ€νŠΈκ°€ μžˆλŠ” 3개의 ν•˜μœ„ 클래슀(예: DashboardFilterTest, DashboardTreeTest, DashboardEditorTest)κ°€ μžˆμŠ΅λ‹ˆλ‹€. λ‚΄ κ²Œμ‹œλ¬Όμ—μ„œ μ„€λͺ…ν•œ μ ‘κ·Ό 방식을 μ‚¬μš©ν•˜μ—¬ ν…ŒμŠ€νŠΈλ₯Ό μ‹€ν–‰ν•  λ•Œλ§ˆλ‹€ ν•΄λ‹Ή 15개의 ν…ŒμŠ€νŠΈκ°€ 3번 이상 μ‹€ν–‰λ©λ‹ˆλ‹€(즉, 3x15 = 45개의 ν…ŒμŠ€νŠΈκ°€ 싀행됨). 15번 ν…ŒμŠ€νŠΈ.

이 경우 DashboardFilterTest, DashboardTreeTest, DashboardEditorTest κ°€ DashboardTest ν™•μž₯ν•˜λŠ” μ΄μœ λŠ” λ¬΄μ—‡μž…λ‹ˆκΉŒ? DashboardTest ν…ŒμŠ€νŠΈλŠ” μ—¬κΈ°μ—μ„œ 상속 μ ‘κ·Ό 방식을 ν™œμš©ν•˜λŠ” λŒ€μ‹  자체 ν΄λž˜μŠ€μ— μžˆμ–΄μ•Ό ν•˜λŠ” 것 κ°™μŠ΅λ‹ˆλ‹€. κΈ°λ³Έ ν΄λž˜μŠ€λŠ” λͺ¨λ“  곡톡 ν…ŒμŠ€νŠΈ λ©”μ„œλ“œλ₯Ό μ œκ±°ν•˜κ³  λ³„λ„μ˜ ν…ŒμŠ€νŠΈ ν΄λž˜μŠ€μ— λ³΄κ΄€ν•˜λ„λ‘ λ¦¬νŒ©ν† λ§ν•΄μ•Ό ν•˜λ©°, DashboardTestλŠ” @Test μ•„λ‹Œ 일반적인 λ©”μ„œλ“œλ§Œ ν¬ν•¨ν•˜λ„λ‘ λ¦¬νŒ©ν† λ§ν•΄μ•Ό ν•©λ‹ˆλ‹€. μ•„λ‹ˆμš”?

이것이 λΆˆκ°€λŠ₯ν•˜λ‹€λ©΄ μ΄ν•΄ν•©λ‹ˆλ‹€. μ–΄μ¨Œλ“  κ°μ‚¬ν•©λ‹ˆλ‹€.

μˆ˜ν–‰ν•  수 μžˆλŠ”μ§€ 여뢀에 λŒ€ν•œ λ¬Έμ œκ°€ μ•„λ‹™λ‹ˆλ‹€(κ΅¬ν˜„ κ³Όμ œλŠ” λ³„λ„μ˜ μ£Όμ œμž„). ν•˜μ§€λ§Œ μ €λŠ” μ—¬μ „νžˆ μ‚¬μš© 사둀 자체의 μœ νš¨μ„±μ„ μ΄ν•΄ν•˜λŠ” 데 어렀움을 κ²ͺκ³  μžˆμŠ΅λ‹ˆλ‹€.

@krmahadevan

이 경우 DashboardFilterTest, DashboardTreeTest, DashboardEditorTest κ°€ DashboardTest ν™•μž₯ν•˜λŠ” μ΄μœ λŠ” λ¬΄μ—‡μž…λ‹ˆκΉŒ? DashboardTest ν…ŒμŠ€νŠΈλŠ” μ—¬κΈ°μ—μ„œ 상속 μ ‘κ·Ό 방식을 ν™œμš©ν•˜λŠ” λŒ€μ‹  자체 ν΄λž˜μŠ€μ— μžˆμ–΄μ•Ό ν•˜λŠ” 것 κ°™μŠ΅λ‹ˆλ‹€. κΈ°λ³Έ ν΄λž˜μŠ€λŠ” λͺ¨λ“  곡톡 ν…ŒμŠ€νŠΈ λ©”μ„œλ“œλ₯Ό μ œκ±°ν•˜κ³  λ³„λ„μ˜ ν…ŒμŠ€νŠΈ ν΄λž˜μŠ€μ— λ³΄κ΄€ν•˜λ„λ‘ λ¦¬νŒ©ν† λ§ν•΄μ•Ό ν•˜λ©°, DashboardTestλŠ” @Test μ•„λ‹Œ 일반적인 λ©”μ„œλ“œλ§Œ ν¬ν•¨ν•˜λ„λ‘ λ¦¬νŒ©ν† λ§ν•΄μ•Ό ν•©λ‹ˆλ‹€. μ•„λ‹ˆμš”?

'DashboardTest'μ—λŠ” μžμ‹ ν΄λž˜μŠ€μ—λ„ ν•„μš”ν•œ λ„μš°λ―Έ λ©”μ„œλ“œ(예: openDashboard(), createDashboard() λ“±)와 setup/teardown/cleanup(@Before/@After) λ©”μ„œλ“œκ°€ ν¬ν•¨λ˜μ–΄ μžˆμŠ΅λ‹ˆλ‹€. λ”°λΌμ„œ μžμ‹ 클래슀의 μ½”λ“œλ₯Ό λ³΅μ œν•  ν•„μš”κ°€ μ—†μŠ΅λ‹ˆλ‹€.
예, 'DashboardTest'의 일뢀 ν…ŒμŠ€νŠΈλŠ” λ‹€λ₯Έ νŠΉμ • 클래슀둜 이동할 수 μžˆμ§€λ§Œ 더 일반적이기 λ•Œλ¬Έμ— 여기에 μœ μ§€ν•˜κ³  μ‹Άμ—ˆμŠ΅λ‹ˆλ‹€(예: λŒ€μ‹œλ³΄λ“œμ˜ 전체 λͺ¨μ–‘ 확인, κΈ°λ³Έ CRUD ν…ŒμŠ€νŠΈ λ˜λŠ” 일뢀 ν…ŒμŠ€νŠΈλŠ” ' t νŠΉμ • 범주에 μ ν•©ν•˜κ±°λ‚˜ ν˜Όν•©).

λ¬Όλ‘ , @Testκ°€ μ•„λ‹Œ ν…ŒμŠ€νŠΈ 클래슀λ₯Ό κ°€μ§ˆ 수 μžˆμ§€λ§Œ(비둝 μ΄μƒν•˜κ³  λˆ„κ΅°κ°€κ°€ μ‹€μˆ˜λ‘œ 여기에 ν…ŒμŠ€νŠΈλ₯Ό μΆ”κ°€ν•  수 μžˆμ§€λ§Œ) 이 문제λ₯Ό ν”Όν•˜κΈ° μœ„ν•œ κ²ƒμž…λ‹ˆλ‹€. λ§žμŠ΅λ‹ˆκΉŒ?

@vlad230

'DashboardTest'μ—λŠ” μžμ‹ ν΄λž˜μŠ€μ—λ„ ν•„μš”ν•œ λ„μš°λ―Έ λ©”μ„œλ“œ(예: openDashboard(), createDashboard() λ“±)와 setup/teardown/cleanup(@Before/@after) λ©”μ„œλ“œκ°€ ν¬ν•¨λ˜μ–΄ μžˆμŠ΅λ‹ˆλ‹€. λ”°λΌμ„œ μžμ‹ 클래슀의 μ½”λ“œλ₯Ό λ³΅μ œν•  ν•„μš”κ°€ μ—†μŠ΅λ‹ˆλ‹€.

이것은 μ˜λ―Έκ°€ μžˆμŠ΅λ‹ˆλ‹€. 그리고 λ„€, κΈ°λ³Έ 클래슀 내에 맀우 잘 상주할 수 μžˆμœΌλ―€λ‘œ ꡬ성 방법을 μžμ‹ ν΄λž˜μŠ€μ—μ„œλ„ μ‚¬μš©ν•  수 μžˆμŠ΅λ‹ˆλ‹€.

예, 'DashboardTest'의 일뢀 ν…ŒμŠ€νŠΈλŠ” λ‹€λ₯Έ νŠΉμ • 클래슀둜 이동할 수 μžˆμ§€λ§Œ 더 일반적이기 λ•Œλ¬Έμ— 여기에 μœ μ§€ν•˜κ³  μ‹Άμ—ˆμŠ΅λ‹ˆλ‹€(예: λŒ€μ‹œλ³΄λ“œμ˜ 전체 λͺ¨μ–‘ 확인, κΈ°λ³Έ CRUD ν…ŒμŠ€νŠΈ λ˜λŠ” 일뢀 ν…ŒμŠ€νŠΈλŠ” ' t νŠΉμ • 범주에 μ ν•©ν•˜κ±°λ‚˜ ν˜Όν•©).

μ—¬μ „νžˆ λͺ¨λ“  일반 @Test λ©”μ„œλ“œλ₯Ό ν¬ν•¨ν•˜λŠ” GenericDashboardTest extends DashboardTest λΌλŠ” 클래슀λ₯Ό λ§Œλ“€ 수 μžˆμŠ΅λ‹ˆλ‹€.

λ¬Όλ‘ , @testκ°€ μ•„λ‹Œ ν…ŒμŠ€νŠΈ 클래슀λ₯Ό κ°€μ§ˆ 수 μžˆμ§€λ§Œ(비둝 μ΄μƒν•˜κ³  λˆ„κ΅°κ°€κ°€ μ‹€μˆ˜λ‘œ 여기에 ν…ŒμŠ€νŠΈλ₯Ό μΆ”κ°€ν•  수 μžˆμ§€λ§Œ) 이 문제λ₯Ό ν”Όν•˜κΈ° μœ„ν•œ κ²ƒμž…λ‹ˆλ‹€. λ§žμŠ΅λ‹ˆκΉŒ?

κΈ€μŽ„, 그것이 μ½”λ“œ 리뷰의 λͺ©μ μ΄ μ•„λ‹ˆκ² λŠ”κ°€ :) μ΄λŸ¬ν•œ λ―Έλ„λŸ¬μ§μ„ λ°©μ§€ν•˜κΈ° μœ„ν•¨μ΄λ‹€. κΈ°λ³Έ 클래슀(μ„€λͺ…ν•œ λ‚΄μš©)μ—λŠ” 일반적인 일반 @Test λ©”μ„œλ“œκ°€ 포함될 ν•„μš”κ°€ μ—†μŠ΅λ‹ˆλ‹€. λ„μš°λ―Έμ™€ κ΅¬μ„±λ§Œ 잘 μˆ˜μš©ν•  수 있으며 κΈ°λ³Έ 클래슀λ₯Ό ν™•μž₯ν•˜κ³  일반 ν…ŒμŠ€νŠΈ λ©”μ„œλ“œλ₯Ό μˆ˜μš©ν•˜λŠ” ν…ŒμŠ€νŠΈ 클래슀λ₯Ό ν•˜λ‚˜ 더 κ°€μ§ˆ 수 μžˆμŠ΅λ‹ˆλ‹€. 그것은 λ‹Ήλ©΄ν•œ ν˜Όλž€μ„ ν•΄κ²°ν•΄μ•Όν•©λ‹ˆλ‹€.

_μ„€κ³„λœ λŒ€λ‘œ μž‘λ™_으둜 ν•΄κ²°ν•˜μ—¬ 이 문제λ₯Ό μ’…λ£Œν•©λ‹ˆλ‹€.

이 νŽ˜μ΄μ§€κ°€ 도움이 λ˜μ—ˆλ‚˜μš”?
0 / 5 - 0 λ“±κΈ‰