Java代码中常见技术债务处理之Exception

写在前面

异常处理是代码中常见的处理,本文根据SonarQube在异常方面的规则和常见检查结果,选取说明了常见异常处理中的技术债务,提倡技术债务最少的编码方式。

Exception handlers should preserve the original exceptions

Either log or rethrow this exception.

When handling a caught exception, the original exception’s message and stack trace should be logged or passed forward.

NONCOMPLIANT CODE EXAMPLE

 // Noncompliant - exception is lost
try { /* ... */ } catch (Exception e) { LOGGER.info("context"); }   

// Noncompliant - exception is lost (only message is preserved)
try { /* ... */ } catch (Exception e) { LOGGER.info(e.getMessage()); }   

// Noncompliant - exception is lost
try { /* ... */ } catch (Exception e) { throw new RuntimeException("context"); }

COMPLIANT SOLUTION

try { /* ... */ } catch (Exception e) { LOGGER.info(e); }   

try { /* ... */ } catch (Exception e) { throw new RuntimeException(e); }

try {
  /* ... */
} catch (RuntimeException e) {
  doSomething();
  throw e;
} catch (Exception e) {
  // Conversion into unchecked exception is also allowed
  throw new RuntimeException(e);
}

错误实例:

 protected int analyzeJobStep1(String jobName) {
        try {
            notifyBHandler();
            return analyzeJobStep2(jobName)
        } catch (Exception e) {
            logger.error(e.getMessage();
        }
         return 0;
    }

解决实例:
    protected int analyzeJobStep1(String jobName) {
        int nRet=0;
        try {
            notifyBHandler();
            nRet = analyzeJobStep2(jobName);
        } catch (Exception e) {
            logger.error("notifyBHandler trigger exception", e);
        }
        return nRet;
    }

Don’t directly use Exception and RuntimeException

Sonarrule:Generic exceptions should never be thrown (squid:S00112)

Using such generic exceptions as Error, RuntimeException, Throwable, and Exception prevents calling methods from handling true, system-generated exceptions differently than application-generated errors.

Noncompliant Code Example

public void foo(String bar) throws Throwable {  // Noncompliant
  throw new RuntimeException("My Message");     // Noncompliant
}

Compliant Solution

public void foo(String bar) {
  throw new MyOwnRuntimeException("My Message");
}

Another related rule: Generic exceptions should never be thrown

the below should be avoided.

@Override
public void myMethod() throws Exception {...}

Define and throw a dedicated exception instead of using a generic one.

Exceptions should not be thrown in finally blocks

try {
  /* some work which end up throwing an exception */
  throw new IllegalArgumentException();
} finally {
  /* clean up */
  throw new RuntimeException();       // Noncompliant; will mask the IllegalArgumentException
}

Compliant Solution

try {
  /* some work which end up throwing an exception */
  throw new IllegalArgumentException();
} finally {
  /* clean up */                                         // Compliant
}

Checked exceptions should not be thrown

The purpose of checked exceptions is to ensure that errors will be dealt with, either by propagating them or by handling them, but some believe that checked exceptions negatively impact the readability of source code, by spreading this error handling/propagation logic everywhere.

This rule verifies that no method throws a new checked exception.

CODE EXAMPLE

public void myMethod1() throws CheckedException {
  ...
  throw new CheckedException(message);   // Noncompliant
  ...
  throw new IllegalArgumentException(message); // Compliant; IllegalArgumentException is unchecked
}   

Solution Example

public void myMethod2() throws CheckedException {  // Compliant; propagation allowed
  myMethod1();
}

Public methods should throw at most one checked exception

Using checked exceptions forces method callers to deal with errors, either by propagating them or by handling them. Throwing exceptions makes them fully part of the API of the method.

But to keep the complexity for callers reasonable, methods should not throw more than one kind of checked exception.

NONCOMPLIANT CODE EXAMPLE

public void delete() throws IOException, SQLException {      // Noncompliant
  /* ... */
}

COMPLIANT SOLUTION

public void delete() throws SomeApplicationLevelException {
  /* ... */
}
时间: 2024-10-03 13:40:04

Java代码中常见技术债务处理之Exception的相关文章

Android如何在java代码中设置margin

习惯了直接在xml里设置margin(距离上下左右都是10dip),如: <ImageView android:layout_margin="10dip" android:src="@drawable/image" /> 只是有些情况下,需要在java代码里来写. API中,android.view.ViewGroup.MarginLayoutParams有个方法setMargins(left, top, right, bottom).可是View本身没

java代码中获取进程process id(转)

另一方面,线程ID=进程ID+内部线程对象ID并不成立,    参考: blog.csdn.net/heyetina/article/details/6633901     如何在java代码中获取进程process id, 实现方法如下所示:    参考: rednaxelafx.iteye.com/blog/716918 http://www.cnblogs.com/mumuxinfei/p/3678854.html

【安卓】在java代码中设置drawableLeft时如何给定合适尺寸?

textView.setCompoundDrawables(drawable, null, null, null);时看不到图片,是因为需要手动给定drawable对应的尺寸,即用drawable.setBounds. 如果该drawable为图片,可直接drawable.setBounds(0,0,drawable.getIntrinsicWidth(),drawable.getIntrinsicHeight());. 即直接给定图片自身尺寸,此时效果和在xml中给定一样. [安卓]在java

如何在java代码中调用一个web项目jsp或者servlet

有时候需要调用一个web项目的jsp或者servlet,但是执行内部的代码,并不是打开jsp,例如需要在一段java代码中清除一个web项目中的缓存,那么可以把清除缓存的代码放在该web项目的一个servlet中,只需要执行如下代码: URL url = new URL("http://192.168.2.123:8080/sace/ClearCache"); url.openStream(); openStream() 执行一次相当于一次URL请求,其中url.openStream(

Java代码中获取Json的key值

测试json字符串: {"access_token":"hkbQl5o_l67dZ7_vJRATKBwTLk9Yj5QyMuOJThAr8Baj0xWf4wxW1p4ym4iTZ3-ptWRRoVtbCNJnyjGLfed_4bB0HiqGP8v-aXOJUUk1tFs","expires_in":7200,"refresh_token":"_or_31yEp8XhxGWvrAzdWIkXfFlKjfb3iTRpfa

Spring MVC框架下在java代码中访问applicationContext.xml文件中配置的文件(可以用于读取配置文件内容)

<bean id="propertyConfigurer" class="com.****.framework.core.SpringPropertiesUtil" lazy-init="false"> <property name="locations"> <list> <value>classpath:config/sys.properties</value> &

关于在Java代码中写Sql语句需要注意的问题

最近做程序,时不时需要自己去手动将sql语句直接写入到Java代码中,写入sql语句时,需要注意几个小问题. 先看我之前写的几句简单的sql语句,自以为没有问题,但是编译直接报错. 1 String str = "insert into XXX(a,b,c) values ('"a.getA()"','"a.getB()"','"a.getC()"');"; 研究了半天发现应该是连接字符串问题,第一次修改过后将赋值字段前后加“

Java web中常见编码乱码问题(二)

根据上篇记录Java web中常见编码乱码问题(一), 接着记录乱码案例: 案例分析:   2.输出流写入内容或者输入流读取内容时乱码(内容中有中文) 原因分析: a. 如果是按字节写入或读取时乱码,应该先检测系统编码是什么样的,看看是否支持中文编码的字符集. System.out.println(System.getProperty("file.encoding")); a1.如果是不支持中文的就要设置jvm编码了,设置方法: Windows环境就在catalina.bat配置: s

Java开发中常见异常整理

算术异常类:ArithmeticExecption 空指针异常类:NullPointerException 类型强制转换异常:ClassCastException 数组负下标异常:NegativeArrayException 数组下标越界异常:ArrayIndexOutOfBoundsException 违背安全原则异常:SecturityException 文件已结束异常:EOFException 文件未找到异常:FileNotFoundException 字符串转换为数字异常:NumberF