Movatterモバイル変換


[0]ホーム

URL:


Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

New rule: Avoid using a FOR LOOP for a query that should return not more than one row #213

Closed
Labels
enhancementNew feature or request
Milestone
@PhilippSalvisberg

Description

@PhilippSalvisberg

This rule was suggested by@dmcghan viaX (Twitter).

Here's an example of a bad SQL:

create or replacefunctionemp_name(in_empnoininteger) returnvarchar2 is   l_enameemp.ename%type;begin<<fetch_name>>   for rin (select enamefrom empwhere empno= in_empno   )   loop      l_ename :=r.ename;   end loop fetch_name;   return l_ename;end emp_name;/

Why is this bad?

  • It can hide atoo_many_rows exception. In case thein_empno is not unique in the underlying model (for whatever reason) the function would return the name of the last fetched row. The more complex the query and the where_clause the higher the risk.
  • It can hide ano_data_found exception. Reading the code it is not clear, if this is wanted. Even if you know that this is often the reason to use a for loop to avoid writing a no_data_found exception handler, we cannot be sure.
  • Intention is lost. The loop is misleading. It implies that a set of rows needs to be processed.

But how can we detect that via static code analysis?

I don't know yet. Static code analysis is based on the source only. No access to the data dictionary. However, there are some cases like in the one above where the fetched data is returned by the function where it should be possible. In the bad example above we know that atoo_many_rows case would lead to a wrong result because the last fetched value is returned. But when the data is passed to a procedure, this cannot be deduced.

In any case, we should not avoid defining a rule just because it is difficult to write an automated check using static code analysis.

And the good example?

Use aselect-into instead. Something like this.

create or replacefunctionemp_name(in_empnoininteger) returnvarchar2 is   l_enameemp.ename%type;beginselect ename     into l_enamefrom empwhere empno= in_empno;   return l_ename;exception   when no_data_found then      returnnull;   when too_many_rows then      raise;end emp_name;/

And in this case, the guidelineG-5060 must be followed. And this makes sense IMO as I stated onX (Twitter). Just because something is hard to test does not mean we should avoid it.

Metadata

Metadata

Assignees

No one assigned

    Labels

    enhancementNew feature or request

    Type

    No type

    Projects

    No projects

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions


      [8]ページ先頭

      ©2009-2025 Movatter.jp