From 4b18d79522e28a357962e9b00a57889a4dd9a4e8 Mon Sep 17 00:00:00 2001
From: Fujii Masao <fujii@postgresql.org>
Date: Thu, 18 Jun 2026 08:27:53 +0900
Subject: [PATCH v1] Refine NULL treatment checks for non-window functions

---
 src/backend/parser/parse_func.c      | 24 +++++++++++++++---------
 src/test/regress/expected/window.out | 17 +++++++++++++++--
 src/test/regress/sql/window.sql      |  3 +++
 3 files changed, 33 insertions(+), 11 deletions(-)

diff --git a/src/backend/parser/parse_func.c b/src/backend/parser/parse_func.c
index 860767a52ee..d78c360ac27 100644
--- a/src/backend/parser/parse_func.c
+++ b/src/backend/parser/parse_func.c
@@ -351,16 +351,16 @@ ParseFuncOrColumn(ParseState *pstate, List *funcname, List *fargs,
 					 errmsg("OVER specified, but %s is not a window function nor an aggregate function",
 							NameListToString(funcname)),
 					 parser_errposition(pstate, location)));
-	}
 
-	/*
-	 * NULL TREATEMENT is only allowed for window functions per spec.
-	 */
-	if (fdresult != FUNCDETAIL_WINDOWFUNC && ignore_nulls != NO_NULLTREATMENT)
-		ereport(ERROR,
-				errcode(ERRCODE_WRONG_OBJECT_TYPE),
-				errmsg("only window functions accept RESPECT/IGNORE NULLS"),
-				parser_errposition(pstate, location));
+		/*
+		 * NULL TREATMENT is only allowed for window functions per spec.
+		 */
+		if (ignore_nulls != NO_NULLTREATMENT)
+			ereport(ERROR,
+					(errcode(ERRCODE_WRONG_OBJECT_TYPE),
+					 errmsg("only window functions accept RESPECT/IGNORE NULLS"),
+					 parser_errposition(pstate, location)));
+	}
 
 	/*
 	 * So far so good, so do some fdresult-type-specific processing.
@@ -386,6 +386,12 @@ ParseFuncOrColumn(ParseState *pstate, List *funcname, List *fargs,
 		catDirectArgs = classForm->aggnumdirectargs;
 		ReleaseSysCache(tup);
 
+		if (ignore_nulls != NO_NULLTREATMENT)
+			ereport(ERROR,
+					(errcode(ERRCODE_WRONG_OBJECT_TYPE),
+					 errmsg("aggregate functions do not accept RESPECT/IGNORE NULLS"),
+					 parser_errposition(pstate, location)));
+
 		/* Now check various disallowed cases. */
 		if (AGGKIND_IS_ORDERED_SET(aggkind))
 		{
diff --git a/src/test/regress/expected/window.out b/src/test/regress/expected/window.out
index 59c3df8cf0a..e129800ab78 100644
--- a/src/test/regress/expected/window.out
+++ b/src/test/regress/expected/window.out
@@ -5748,6 +5748,19 @@ WINDOW w AS (ORDER BY name ROWS BETWEEN 2 PRECEDING AND 2 FOLLOWING EXCLUDE CURR
 (10 rows)
 
 -- valid and invalid functions
+SELECT abs(1) IGNORE NULLS; -- fails
+ERROR:  only window functions accept RESPECT/IGNORE NULLS
+LINE 1: SELECT abs(1) IGNORE NULLS;
+               ^
+SELECT no_such_window_func() IGNORE NULLS; -- fails, but not because of null treatment
+ERROR:  function no_such_window_func() does not exist
+LINE 1: SELECT no_such_window_func() IGNORE NULLS;
+               ^
+DETAIL:  There is no function of that name.
+SELECT sum(orbit) IGNORE NULLS FROM planets; -- fails
+ERROR:  aggregate functions do not accept RESPECT/IGNORE NULLS
+LINE 1: SELECT sum(orbit) IGNORE NULLS FROM planets;
+               ^
 SELECT sum(orbit) OVER () FROM planets; -- succeeds
   sum   
 --------
@@ -5764,11 +5777,11 @@ SELECT sum(orbit) OVER () FROM planets; -- succeeds
 (10 rows)
 
 SELECT sum(orbit) RESPECT NULLS OVER () FROM planets; -- fails
-ERROR:  only window functions accept RESPECT/IGNORE NULLS
+ERROR:  aggregate functions do not accept RESPECT/IGNORE NULLS
 LINE 1: SELECT sum(orbit) RESPECT NULLS OVER () FROM planets;
                ^
 SELECT sum(orbit) IGNORE NULLS OVER () FROM planets; -- fails
-ERROR:  only window functions accept RESPECT/IGNORE NULLS
+ERROR:  aggregate functions do not accept RESPECT/IGNORE NULLS
 LINE 1: SELECT sum(orbit) IGNORE NULLS OVER () FROM planets;
                ^
 SELECT row_number() OVER () FROM planets; -- succeeds
diff --git a/src/test/regress/sql/window.sql b/src/test/regress/sql/window.sql
index 17261135dc3..5ac3a486e16 100644
--- a/src/test/regress/sql/window.sql
+++ b/src/test/regress/sql/window.sql
@@ -2099,6 +2099,9 @@ WINDOW w AS (ORDER BY name ROWS BETWEEN 2 PRECEDING AND 2 FOLLOWING EXCLUDE CURR
 ;
 
 -- valid and invalid functions
+SELECT abs(1) IGNORE NULLS; -- fails
+SELECT no_such_window_func() IGNORE NULLS; -- fails, but not because of null treatment
+SELECT sum(orbit) IGNORE NULLS FROM planets; -- fails
 SELECT sum(orbit) OVER () FROM planets; -- succeeds
 SELECT sum(orbit) RESPECT NULLS OVER () FROM planets; -- fails
 SELECT sum(orbit) IGNORE NULLS OVER () FROM planets; -- fails
-- 
2.53.0

