Bruce Momjian wrote:

OK, added to TODO:

        Modify pg_get_triggerdef() to take a boolean to pretty-print,
        and use that as part of pg_dump along with psql

Andreas, can you work on this?  I like the idea of removing extra
parens, and merging it into the existing code rather than into contrib
makes sense.


Yes, I can. At the moment, I have a runnable contrib module, which replaces all pg_get_xxxdef by pg_get_xxxdef2 functions. It's no problem to apply that code back to the original ruleutils.c when the isSimpleNode algorithm is reviewed independently and proved being correct.


For safety reasons, I can make this dependent on a bool pretty-print parameter.

I also could implement line break and indentation formatting. I implemented a keyword-based algorithm in pgAdmin3, and having the original tree the job is obviously easier. Do we need any flexibility about indent char (tab or space) and indentation size (2 chars)? The pgAdmin3 algorithm uses 4 spaces, and tries to align keywords so they line up nicely, and I'd prefer doing it this way again.

SELECT foo
FROM bar b
JOIN chair c USING (thekeycol)
WHERE ...



Regards,


Andreas

/***************************************
* check if given node is simple.
*  false  : not simple
*  true   : simple in the context of parent node's type
***************************************/

static bool isSimpleNode(Node *node, NodeTag parentNodeType)
{
   if (!node)
        return true;

   switch (nodeTag(node))
   {
        // single words: always simple
        case T_Var:
        case T_Const:
        case T_Param:

        // function-like: name(..) or name[..]
        case T_ArrayRef:
        case T_FuncExpr:
        case T_ArrayExpr:
        case T_CoalesceExpr:
        case T_NullIfExpr:
        case T_Aggref:

       // CASE keywords act as parentheses
        case T_CaseExpr:
            return true;

       // appears simple since . has top precedence, unless parent is T_FieldSelect 
itself!
        case T_FieldSelect:
            return (parentNodeType == T_FieldSelect ? false : true);


// maybe simple, check args case T_CoerceToDomain: return isSimpleNode((Node*) ((CoerceToDomain*)node)->arg, T_CoerceToDomain); case T_RelabelType: return isSimpleNode((Node*) ((RelabelType*)node)->arg, T_RelabelType);


// depends on parent node type; needs further checking case T_SubLink: case T_NullTest: case T_BooleanTest: case T_OpExpr: case T_DistinctExpr: if (parentNodeType == T_BoolExpr) return true; // else check the same as for T_BoolExpr; no break here! case T_BoolExpr: switch (parentNodeType) { case T_ArrayRef: case T_FuncExpr: case T_ArrayExpr: case T_CoalesceExpr: case T_NullIfExpr: case T_Aggref: case T_CaseExpr: return true; default: break; } return false;

       // these are not completely implemented; so far, they're simple
        case T_SubPlan:
        case T_CoerceToDomainValue:
            return true;

        default:
            break;
   }
   // those we don't know: in dubio complexo
   return false;
}





---------------------------(end of broadcast)---------------------------
TIP 5: Have you checked our extensive FAQ?

http://www.postgresql.org/docs/faqs/FAQ.html

Reply via email to