Question

I want to use a alias for webApp2 self.response.out.write or self.response.write function. Like

from __future__ import print_function
class M:
    def __init__(self):
        self.echo ( 'BOO BOO')
    def f(self, data ) :
        print ( data )
    echo = f

a = M()
a.echo(' ALIASED FUNCTION ' )

I tried

class Main(webapp2.RequestHandler):

    def fun(self):
        self.response.out.write ( 'FUNNY' )

    def get(self):
        self.response.headers['Content-Type'] = 'text/html'
        self.response.write( 'DERIVED CLASS' )
        self.aliasOut()
        self.aliasFun()

    def post(self):
        pass

    aliasOut =  response.out.write   # NameError: name 'response' is not defined
    aliasFun =  fun                  # This works
Était-ce utile?

La solution

The issue you're running into is that self is a local variable whithin each method. You can't make a class variable holding self.response.out.write because self is undefined at the top level of the class. I think there are two possible solutions:

The simplest is to just make a local alias in any method that is going to call self.response.out.write a lot:

def i_write_a_lot(self):
    alias = self.response.out.write
    alias("stuff")
    alias("more stuff")
    alias("yet more stuff")

Another option would be to make the alias a property object in the class, so it can be accessed anywhere in the class. This is much less obvious about where the alias comes from, which may cause confusion when somebody else (or you, months later) reads your code, but it comes closer to what you wanted:

@property
def alias(self):
    return self.response.out.write

def method1(self):
    self.alias("stuff")

def method2(self):
    self.alias("other stuff")

Autres conseils

Thanks @Blckknght, two methods you suggested all of them work.

I know it would be confusing. I modified your code to make it a less confusing :) The complete minimal AppEngine template is here:

#!/usr/bin/env python
import webapp2


class MainHandler(webapp2.RequestHandler):

   def get(self):
       self.echo('BOO BOO')
       self.echoHtml( ' METHOD 2 ')
       # To save more key strokes. I improved it slightly.  Trust me, I tested it :)
       echo = self.echo
       echoHtml = self.echoHtml
       echo ( 'HORA ')
       echoHtml ( 'HAYDAAA ! ') 

   def echo(self, context):
       alias = self.response.out.write
       alias( context )

   @property
   def echoHtml(self):
       return self.response.out.write




app = webapp2.WSGIApplication([
    ('/', MainHandler)
], debug=True)

I came another solution, i created a base class for WebApp2Request Handler, and used this base class instead of webapp2.RequestHandler

import webapp2

class Webapp2FactoryClass(webapp2.RequestHandler):    
    def echo(self, context):
        self.response.out.write(context)

    def __init__(self, *args, **kwargs):
        super(Webapp2FactoryClass, self).__init__(*args, **kwargs)
        self.args = args
        self.kwargs = kwargs

class MainHandler(Webapp2FactoryClass):    
    def __init__(self, *args, **kwargs):
        super(MainHandler, self).__init__(*args, **kwargs)
        self.args = args
        self.kwargs = kwargs

    def get(self, *args, **kwargs):
        self.echo('Bumbala')
Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top