Here is a simple way to re-express something as a polynomial in var:
polyform(expr,var):= ev(ratdisrep(rat(isolate(expr,var),var)),eval);
If there are non-polynomial parts, they end up in the 0th order
(constant) polynomial term.
I don't much like the way it uses "ev" to substitute back the
E-variables, but I don't know any simple way of making that cleaner.
This means that the variables in your expression should not have been
assigned values.
Here are some examples comparing polyform to rat:
ex: x*(y+1)^3-(x+1)*a;
rat(ex,x) => (y^3+3*y^2+3*y-a+1)*x-a
-- expands y subexpression unnecessarily
polyform(ex,x) => x*((y+1)^3-a)-a
-- does not expand y terms
rat(ex,y) => x*y^3+3*x*y^2+3*x*y+(-a+1)*x-a
-- canonicalizes x terms
polyform(ex,y) => x*y^3+3*x*y^2+3*x*y-a*(x+1)+x
-- does not combine x terms
rat(ex,a) => (-x-1)*a+x*y^3+3*x*y^2+3*x*y+x
polyform(ex,a) => x*(y+1)^3+a*(-x-1)
-- does not expand
-- though the a^1 term does not appear first, the exprssion
-- is nonetheless a polynomial in a.
-- This has to do with Maxima's variable order canonicalization
rat(ex,xxx) => x*y^3+3*x*y^2+3*x*y+(-a+1)*x-a
-- expands unnecessarily
polyform(ex,xxx) => x*(y+1)^3-a*(x+1)
-- leaves expression untouched