checkFunctionUsage checks whether a given built-in function is allowed in the current context.
(expr *FuncExpr, def *FunctionDefinition)
| 739 | // checkFunctionUsage checks whether a given built-in function is |
| 740 | // allowed in the current context. |
| 741 | func (sc *SemaContext) checkFunctionUsage(expr *FuncExpr, def *FunctionDefinition) error { |
| 742 | if def.UnsupportedWithIssue != 0 { |
| 743 | // Note: no need to embed the function name in the message; the |
| 744 | // caller will add the function name as prefix. |
| 745 | const msg = "this function is not yet supported" |
| 746 | if def.UnsupportedWithIssue < 0 { |
| 747 | return unimplemented.New(def.Name+"()", msg) |
| 748 | } |
| 749 | return unimplemented.NewWithIssueDetail(def.UnsupportedWithIssue, def.Name, msg) |
| 750 | } |
| 751 | if def.Private { |
| 752 | return pgerror.Wrapf(errPrivateFunction, pgcode.ReservedName, |
| 753 | "%s()", errors.Safe(def.Name)) |
| 754 | } |
| 755 | if sc == nil { |
| 756 | // We can't check anything further. Give up. |
| 757 | return nil |
| 758 | } |
| 759 | |
| 760 | if expr.IsWindowFunctionApplication() { |
| 761 | if sc.Properties.required.rejectFlags&RejectWindowApplications != 0 { |
| 762 | return NewInvalidFunctionUsageError(WindowClass, sc.Properties.required.context) |
| 763 | } |
| 764 | |
| 765 | if sc.Properties.Derived.InWindowFunc && |
| 766 | sc.Properties.required.rejectFlags&RejectNestedWindowFunctions != 0 { |
| 767 | return pgerror.Newf(pgcode.Windowing, "window function calls cannot be nested") |
| 768 | } |
| 769 | sc.Properties.Derived.SeenWindowApplication = true |
| 770 | } else { |
| 771 | // If it is an aggregate function *not used OVER a window*, then |
| 772 | // we have an aggregation. |
| 773 | if def.Class == AggregateClass { |
| 774 | if sc.Properties.Derived.inFuncExpr && |
| 775 | sc.Properties.required.rejectFlags&RejectNestedAggregates != 0 { |
| 776 | return NewAggInAggError() |
| 777 | } |
| 778 | if sc.Properties.required.rejectFlags&RejectAggregates != 0 { |
| 779 | return NewInvalidFunctionUsageError(AggregateClass, sc.Properties.required.context) |
| 780 | } |
| 781 | sc.Properties.Derived.SeenAggregate = true |
| 782 | } |
| 783 | } |
| 784 | if def.Class == GeneratorClass { |
| 785 | if sc.Properties.Derived.inFuncExpr && |
| 786 | sc.Properties.required.rejectFlags&RejectNestedGenerators != 0 { |
| 787 | return NewInvalidNestedSRFError(sc.Properties.required.context) |
| 788 | } |
| 789 | if sc.Properties.required.rejectFlags&RejectGenerators != 0 { |
| 790 | return NewInvalidFunctionUsageError(GeneratorClass, sc.Properties.required.context) |
| 791 | } |
| 792 | sc.Properties.Derived.SeenGenerator = true |
| 793 | } |
| 794 | return nil |
| 795 | } |
| 796 | |
| 797 | // checkVolatility checks whether an operator with the given volatility is |
| 798 | // allowed in the current context. |
no test coverage detected