fixed @//// in wiki and pep8 spacing
This commit is contained in:
@@ -1 +1 @@
|
||||
Version 2.00.0 (2012-08-25 11:25:55) dev
|
||||
Version 2.00.0 (2012-08-25 11:29:08) dev
|
||||
|
||||
@@ -6,3 +6,5 @@
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -309,3 +309,4 @@ if __name__=='__main__':
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -6,3 +6,4 @@ def webapp_add_wsgi_middleware(app):
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -65,3 +65,4 @@ wsgiref.handlers.CGIHandler().run(gluon.main.wsgibase)
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -55,3 +55,4 @@ fcgi.WSGIServer(application, bindAddress='/tmp/fcgi.sock').run()
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -103,3 +103,4 @@ if __name__ == '__main__':
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -52,3 +52,4 @@ if 0:
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -480,3 +480,4 @@ def create_missing_app_folders(request):
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -498,3 +498,4 @@ def lazy_cache(key=None,time_expire=None,cache_model='ram'):
|
||||
return decorator
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -56,3 +56,4 @@ def getcfs(key, filename, filter=None):
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -691,3 +691,4 @@ if __name__ == '__main__':
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -723,3 +723,4 @@ def contenttype(filename, default='text/plain'):
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -263,3 +263,4 @@ if __name__=='__main__':
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -243,3 +243,4 @@ if __name__=='__main__':
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -5,3 +5,4 @@
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -501,3 +501,4 @@ aes_Rcon = array('B',
|
||||
'61c29f254a943366cc831d3a74e8cb'.decode('hex')
|
||||
)
|
||||
|
||||
|
||||
|
||||
@@ -135,7 +135,7 @@ def oembed(url):
|
||||
for k,v in EMBED_MAPS:
|
||||
if k.match(url):
|
||||
oembed = v+'?format=json&url='+cgi.escape(url)
|
||||
try:
|
||||
try:
|
||||
data = urllib.urlopen(oembed).read()
|
||||
print data
|
||||
return loads(data) # json!
|
||||
@@ -152,7 +152,7 @@ def expand_one(url,cdict):
|
||||
r = cdict[url]
|
||||
else:
|
||||
r = oembed(url)
|
||||
if isinstance(cdict,dict):
|
||||
if isinstance(cdict,dict):
|
||||
cdict[url] = r
|
||||
# if oembed service
|
||||
if 'html' in r:
|
||||
@@ -204,3 +204,4 @@ if __name__=="__main__":
|
||||
else:
|
||||
print test()
|
||||
|
||||
|
||||
|
||||
@@ -194,3 +194,4 @@ if __name__ == "__main__":
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -3910,3 +3910,4 @@ def parse(url_file_stream_or_string, etag=None, modified=None, agent=None, refer
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -55,3 +55,4 @@ class MemcacheClient(Client):
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -90,3 +90,4 @@ def autoretry_datastore_timeouts(attempts=5.0, interval=0.1, exponent=2.0):
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -67,3 +67,4 @@ def pdf_from_html(html):
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -19,3 +19,4 @@ def button(merchant_id="123456789012345",
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -9,3 +9,4 @@ from gluon.dal import DAL, Field, Table, Query, Set, Expression, Row, Rows, driv
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -58,3 +58,4 @@ def THUMB(image, nx=120, ny=120, gae=False, name='thumb'):
|
||||
else:
|
||||
return image
|
||||
|
||||
|
||||
|
||||
@@ -1,2 +1,3 @@
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -23,3 +23,4 @@ def basic_auth(server="http://127.0.0.1"):
|
||||
return False
|
||||
return basic_login_aux
|
||||
|
||||
|
||||
|
||||
@@ -6,18 +6,18 @@
|
||||
developed by Madhukar R Pai (Copyright 2012)
|
||||
Email <madspai@gmail.com>
|
||||
License : LGPL
|
||||
|
||||
|
||||
thanks and credits to the web2py community
|
||||
|
||||
|
||||
This custom authenticator allows web2py to authenticate using browserid (https://browserid.org/)
|
||||
BrowserID is a project by Mozilla Labs (http://mozillalabs.com/)
|
||||
to Know how browserid works please visit http://identity.mozilla.com/post/7616727542/introducing-browserid-a-better-way-to-sign-in
|
||||
|
||||
|
||||
bottom line BrowserID provides a free, secure, de-centralized, easy to use(for users and developers) login solution.
|
||||
You can use any email id as your login id. Browserid just verifys the email id and lets you login with that id.
|
||||
|
||||
|
||||
credits for the doPost jquery function - itsadok (http://stackoverflow.com/users/7581/itsadok)
|
||||
|
||||
|
||||
"""
|
||||
import time
|
||||
from gluon import *
|
||||
@@ -32,7 +32,7 @@ class BrowserID(object):
|
||||
audience = "http://127.0.0.1:8000"
|
||||
assertion_post_url = "http://127.0.0.1:8000/%s/default/user/login" % request.application)
|
||||
"""
|
||||
|
||||
|
||||
def __init__(self,
|
||||
request,
|
||||
audience = "",
|
||||
@@ -45,7 +45,7 @@ class BrowserID(object):
|
||||
crypto_js = "https://crypto-js.googlecode.com/files/2.2.0-crypto-md5.js",
|
||||
on_login_failure = None,
|
||||
):
|
||||
|
||||
|
||||
self.request = request
|
||||
self.audience = audience
|
||||
self.assertion_post_url = assertion_post_url
|
||||
@@ -64,13 +64,13 @@ class BrowserID(object):
|
||||
|
||||
def get_user(self):
|
||||
request = self.request
|
||||
if request.vars.assertion:
|
||||
if request.vars.assertion:
|
||||
audience = self.audience
|
||||
issuer = self.issuer
|
||||
assertion = XML(request.vars.assertion,sanitize=True)
|
||||
verify_data = {'assertion':assertion,'audience':audience}
|
||||
auth_info_json = fetch(self.verify_url,data=verify_data)
|
||||
j = json.loads(auth_info_json)
|
||||
j = json.loads(auth_info_json)
|
||||
epoch_time = int(time.time()*1000) # we need 13 digit epoch time
|
||||
if j["status"] == "okay" and j["audience"] == audience and j['issuer'] == issuer and j['expires'] >= epoch_time:
|
||||
return dict(email = j['email'])
|
||||
@@ -88,3 +88,4 @@ class BrowserID(object):
|
||||
A(IMG(_src=self.browserid_button,_alt=self.prompt),_href="#",_onclick=onclick,_class="browserid",_title="Login With BrowserID"),
|
||||
SCRIPT(self.asertion_js))
|
||||
return form
|
||||
|
||||
|
||||
@@ -136,3 +136,4 @@ class CasAuth( object ):
|
||||
import urllib
|
||||
redirect("%s?service=%s" % (self.cas_logout_url,self.cas_my_url))
|
||||
|
||||
|
||||
|
||||
@@ -12,7 +12,7 @@
|
||||
import os
|
||||
import re
|
||||
import urllib
|
||||
from dropbox import client, rest, session
|
||||
from dropbox import client, rest, session
|
||||
from gluon import *
|
||||
from gluon.tools import fetch
|
||||
from gluon.storage import Storage
|
||||
@@ -50,15 +50,15 @@ class DropboxAccount(object):
|
||||
self.sess = session.DropboxSession(
|
||||
self.key,self.secret,self.access_type)
|
||||
|
||||
|
||||
|
||||
def get_user(self):
|
||||
request = self.request
|
||||
token = current.session.dropbox_token
|
||||
try:
|
||||
access_token = self.sess.obtain_access_token(token)
|
||||
access_token = self.sess.obtain_access_token(token)
|
||||
except:
|
||||
access_token = None
|
||||
if access_token:
|
||||
if access_token:
|
||||
user = Storage()
|
||||
self.client = client.DropboxClient(self.sess)
|
||||
data = self.client.account_info()
|
||||
@@ -68,7 +68,7 @@ class DropboxAccount(object):
|
||||
last_name = display_name[-1],
|
||||
registration_id = data.get('uid',None))
|
||||
if not user['registration_id'] and self.on_login_failure:
|
||||
redirect(self.on_login_failure)
|
||||
redirect(self.on_login_failure)
|
||||
return user
|
||||
return None
|
||||
|
||||
@@ -107,3 +107,4 @@ def use_dropbox(auth,filename='private/dropbox.key',**kwargs):
|
||||
auth.settings.login_form = DropboxAccount(
|
||||
request,key=key,secret=secret,access_type=access_type,
|
||||
login_url = login_url,**kwargs)
|
||||
|
||||
|
||||
@@ -43,3 +43,4 @@ def email_auth(server="smtp.gmail.com:587",
|
||||
pass
|
||||
return False
|
||||
return email_auth_aux
|
||||
|
||||
|
||||
@@ -86,7 +86,7 @@ class ExtendedLoginForm(object):
|
||||
Otherwise it will render the normal login form combined with
|
||||
alt_login_form.login_form.
|
||||
"""
|
||||
|
||||
|
||||
request = current.request
|
||||
args = request.args
|
||||
|
||||
@@ -102,3 +102,4 @@ class ExtendedLoginForm(object):
|
||||
form.components.append(self.alt_login_form.login_form())
|
||||
return form
|
||||
|
||||
|
||||
|
||||
@@ -36,3 +36,4 @@ class GaeGoogleAccount(object):
|
||||
return dict(nickname=user.nickname(), email=user.email(),
|
||||
user_id=user.user_id(), source="google account")
|
||||
|
||||
|
||||
|
||||
@@ -634,3 +634,4 @@ def ldap_auth(server='ldap', port=None,
|
||||
if filterstr[0] == '(' and filterstr[-1] == ')': # rfc4515 syntax
|
||||
filterstr = filterstr[1:-1] # parens added again where used
|
||||
return ldap_auth_aux
|
||||
|
||||
|
||||
@@ -49,3 +49,4 @@ class LinkedInAccount(object):
|
||||
username = profile.id)
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -110,3 +110,4 @@ class Loginza(object):
|
||||
SCRIPT(_src="https://s3-eu-west-1.amazonaws.com/s1.loginza.ru/js/widget.js", _type="text/javascript"))
|
||||
return form
|
||||
|
||||
|
||||
|
||||
@@ -6,24 +6,24 @@ from gluon.dal import DAL
|
||||
|
||||
def motp_auth(db=DAL('sqlite://storage.sqlite'),
|
||||
time_offset=60):
|
||||
|
||||
|
||||
"""
|
||||
motp allows you to login with a one time password(OTP) generated on a motp client,
|
||||
motp allows you to login with a one time password(OTP) generated on a motp client,
|
||||
motp clients are available for practically all platforms.
|
||||
to know more about OTP visit http://en.wikipedia.org/wiki/One-time_password
|
||||
to know more visit http://motp.sourceforge.net
|
||||
|
||||
|
||||
|
||||
|
||||
Written by Madhukar R Pai (madspai@gmail.com)
|
||||
License : MIT or GPL v2
|
||||
|
||||
|
||||
thanks and credits to the web2py community
|
||||
|
||||
|
||||
to use motp_auth:
|
||||
motp_auth.py has to be located in gluon/contrib/login_methods/ folder
|
||||
first auth_user has to have 2 extra fields - motp_secret and motp_pin
|
||||
for that define auth like shown below:
|
||||
|
||||
|
||||
## after auth = Auth(db)
|
||||
db.define_table(
|
||||
auth.settings.table_user_name,
|
||||
@@ -42,7 +42,7 @@ def motp_auth(db=DAL('sqlite://storage.sqlite'),
|
||||
writable=False, readable=False, default=''),
|
||||
Field('registration_id', length=512, # required
|
||||
writable=False, readable=False, default=''))
|
||||
|
||||
|
||||
##validators
|
||||
custom_auth_table = db[auth.settings.table_user_name] # get the custom_auth_table
|
||||
custom_auth_table.first_name.requires = \
|
||||
@@ -53,22 +53,22 @@ def motp_auth(db=DAL('sqlite://storage.sqlite'),
|
||||
custom_auth_table.email.requires = [
|
||||
IS_EMAIL(error_message=auth.messages.invalid_email),
|
||||
IS_NOT_IN_DB(db, custom_auth_table.email)]
|
||||
|
||||
|
||||
auth.settings.table_user = custom_auth_table # tell auth to use custom_auth_table
|
||||
## before auth.define_tables()
|
||||
|
||||
##after that:
|
||||
|
||||
|
||||
##after that:
|
||||
|
||||
from gluon.contrib.login_methods.motp_auth import motp_auth
|
||||
auth.settings.login_methods.append(motp_auth(db=db))
|
||||
|
||||
|
||||
##Instructions for using MOTP
|
||||
- after configuring motp for web2py, Install a MOTP client on your phone (android,IOS, java, windows phone, etc)
|
||||
- initialize the motp client (to reset a motp secret type in #**#),
|
||||
- initialize the motp client (to reset a motp secret type in #**#),
|
||||
During user creation enter the secret generated during initialization into the motp_secret field in auth_user and
|
||||
similarly enter a pre-decided pin into the motp_pin
|
||||
- done.. to login, just generate a fresh OTP by typing in the pin and use the OTP as password
|
||||
|
||||
|
||||
###To Dos###
|
||||
- both motp_secret and pin are stored in plain text! need to have some way of encrypting
|
||||
- web2py stores the password in db on successful login (should not happen)
|
||||
@@ -85,7 +85,7 @@ def motp_auth(db=DAL('sqlite://storage.sqlite'),
|
||||
hash = md5(to_hash).hexdigest()[:6]
|
||||
if otp == hash: return True
|
||||
return False
|
||||
|
||||
|
||||
def motp_auth_aux(email,
|
||||
password,
|
||||
db=db,
|
||||
@@ -102,3 +102,4 @@ def motp_auth(db=DAL('sqlite://storage.sqlite'),
|
||||
else: return False
|
||||
return False
|
||||
return motp_auth_aux
|
||||
|
||||
|
||||
@@ -188,3 +188,4 @@ class OAuthAccount(object):
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -66,7 +66,7 @@ class OAuthAccount(object):
|
||||
|
||||
if not self.accessToken():
|
||||
return None
|
||||
|
||||
|
||||
if not self.graph:
|
||||
self.graph = GraphAPI((self.accessToken()))
|
||||
|
||||
@@ -117,7 +117,7 @@ server for requests. It can be used for the optional"scope" parameters for Face
|
||||
"""
|
||||
Build the url opener for managing HTTP Basic Athentication
|
||||
"""
|
||||
# Create an OpenerDirector with support
|
||||
# Create an OpenerDirector with support
|
||||
# for Basic HTTP Authentication...
|
||||
|
||||
auth_handler = urllib2.HTTPBasicAuthHandler()
|
||||
@@ -172,7 +172,7 @@ server for requests. It can be used for the optional"scope" parameters for Face
|
||||
if current.session.token.has_key('expires_in'):
|
||||
exps = 'expires_in'
|
||||
elif current.session.token.has_key('expires'):
|
||||
exps = 'expires'
|
||||
exps = 'expires'
|
||||
else:
|
||||
exps = None
|
||||
current.session.token['expires'] = exps and \
|
||||
@@ -185,7 +185,7 @@ server for requests. It can be used for the optional"scope" parameters for Face
|
||||
current.session.token = None
|
||||
return None
|
||||
|
||||
def __init__(self, g=None,
|
||||
def __init__(self, g=None,
|
||||
client_id=None, client_secret=None,
|
||||
auth_url=None, token_url=None, **args):
|
||||
"""
|
||||
@@ -215,7 +215,7 @@ server for requests. It can be used for the optional"scope" parameters for Face
|
||||
def get_user(self):
|
||||
"""
|
||||
Override this method by sublcassing the class.
|
||||
|
||||
|
||||
"""
|
||||
if not current.session.token: return None
|
||||
return dict(first_name = 'Pinco',
|
||||
@@ -274,3 +274,4 @@ server for requests. It can be used for the optional"scope" parameters for Face
|
||||
return current.session.code
|
||||
return None
|
||||
|
||||
|
||||
|
||||
@@ -630,3 +630,4 @@ class Web2pyStore(OpenIDStore):
|
||||
return self.cleanupNonces(), self.cleanupAssociations()
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -20,3 +20,4 @@ def pam_auth():
|
||||
|
||||
return pam_auth_aux
|
||||
|
||||
|
||||
|
||||
@@ -53,12 +53,12 @@ class RPXAccount(object):
|
||||
self.prompt = prompt
|
||||
self.on_login_failure = on_login_failure
|
||||
self.mappings = Storage()
|
||||
|
||||
|
||||
dn = {'givenName':'','familyName':''}
|
||||
self.mappings.Facebook = lambda profile, dn=dn:\
|
||||
dict(registration_id = profile.get("identifier",""),
|
||||
username = profile.get("preferredUsername",""),
|
||||
email = profile.get("email",""),
|
||||
email = profile.get("email",""),
|
||||
first_name = profile.get("name",dn).get("givenName",""),
|
||||
last_name = profile.get("name",dn).get("familyName",""))
|
||||
self.mappings.Google = lambda profile, dn=dn:\
|
||||
@@ -125,3 +125,4 @@ def use_janrain(auth,filename='private/janrain.key',**kwargs):
|
||||
['register','change_password','request_reset_password']
|
||||
auth.settings.login_form = RPXAccount(
|
||||
request, api_key=key,domain=domain, url = url,**kwargs)
|
||||
|
||||
|
||||
@@ -53,7 +53,7 @@ class X509Auth(object):
|
||||
# cn = self.subject.cn
|
||||
self.subject = Storage(filter(None,
|
||||
map(lambda x:
|
||||
(x,map(lambda y:
|
||||
(x,map(lambda y:
|
||||
y.get_data().as_text(),
|
||||
subject.get_entries_by_nid(subject.nid[x]))),
|
||||
subject.nid.keys())))
|
||||
@@ -63,7 +63,7 @@ class X509Auth(object):
|
||||
def login_form(self, **args):
|
||||
raise HTTP(403,'Login not allowed. No valid x509 crentials')
|
||||
|
||||
|
||||
|
||||
|
||||
def login_url(self, next="/"):
|
||||
raise HTTP(403,'Login not allowed. No valid x509 crentials')
|
||||
@@ -102,3 +102,4 @@ class X509Auth(object):
|
||||
return profile
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -801,7 +801,7 @@ def render(text,
|
||||
# this is experimental @{function/args}
|
||||
# turns into a digitally signed URL
|
||||
def u1(match,URL=URL):
|
||||
a,c,f,args = match.group('a','c','f','args')
|
||||
a,c,f,args = match.group('a','c','f','args')
|
||||
return URL(a=a or None,c=c or None,f = f or None,
|
||||
args=args.split('/'), scheme=True, host=True)
|
||||
text = regex_URL.sub(u1,text)
|
||||
|
||||
@@ -911,3 +911,4 @@ if __name__ == '__main__':
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -127,3 +127,4 @@ if __name__ == "__main__":
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -129,3 +129,4 @@ def test():
|
||||
if __name__ == '__main__':
|
||||
test()
|
||||
|
||||
|
||||
|
||||
@@ -171,3 +171,4 @@ if __name__ == '__main__':
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -9,3 +9,4 @@ from fpdf import *
|
||||
|
||||
# import warnings
|
||||
# warnings.warn("pyfpdf package name is deprecated, please use fpdf instead")
|
||||
|
||||
|
||||
@@ -964,3 +964,4 @@ if __name__ == '__main__':
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -167,3 +167,4 @@ class RedisClient(object):
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -592,3 +592,4 @@ if __name__ == '__main__':
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -270,3 +270,4 @@ if __name__=='__main__':
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -151,3 +151,4 @@ if __name__ == "__main__":
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -116,3 +116,4 @@ def sms_email(number,provider):
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -879,3 +879,4 @@ if __name__ == '__main__':
|
||||
print s['c'].computed_value
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -66,3 +66,4 @@ if __name__=='__main__':
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -247,3 +247,4 @@ class TaskBarIcon:
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -95,3 +95,4 @@ if __name__=='__main__':
|
||||
print(t.getReportText(orderByCost=False))
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -520,3 +520,4 @@ class mobilize(object):
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -329,3 +329,4 @@ class _Web2pyDateTrackerImporter(_Web2pyImporter, _DateTrackerImporter):
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
+7
-6
@@ -6932,7 +6932,7 @@ def index():
|
||||
tablename,
|
||||
*fields,
|
||||
**args
|
||||
):
|
||||
):
|
||||
if not isinstance(tablename,str):
|
||||
raise SyntaxError, "missing table name"
|
||||
elif tablename.startswith('_') or hasattr(self,tablename) or \
|
||||
@@ -6946,7 +6946,7 @@ def index():
|
||||
invalid_args = [key for key in args if not key in TABLE_ARGS]
|
||||
if invalid_args:
|
||||
raise SyntaxError, 'invalid table "%s" attributes: %s' \
|
||||
% (tablename,invalid_args)
|
||||
% (tablename,invalid_args)
|
||||
if self._lazy_tables and not tablename in self._LAZY_TABLES:
|
||||
self._LAZY_TABLES[tablename] = (tablename,fields,args)
|
||||
table = None
|
||||
@@ -6985,7 +6985,7 @@ def index():
|
||||
sql_locker.release()
|
||||
else:
|
||||
table._dbt = None
|
||||
on_define = args.get('on_define',None)
|
||||
on_define = args.get('on_define',None)
|
||||
if on_define: on_define(table)
|
||||
return table
|
||||
|
||||
@@ -7065,7 +7065,7 @@ def index():
|
||||
to or instead of including Field objects, or it can be just a single
|
||||
table (not in a list). In that case, the Field objects will be
|
||||
extracted from the table(s).
|
||||
|
||||
|
||||
The field names will be extracted from the Field objects, or optionally,
|
||||
a list of field names can be provided (in tablename.fieldname format)
|
||||
via the "colnames" argument. Note, the fields and colnames must be in
|
||||
@@ -7100,7 +7100,7 @@ def index():
|
||||
else:
|
||||
extracted_fields.append(field)
|
||||
if not colnames:
|
||||
colnames = ['%s.%s' % (f.tablename, f.name)
|
||||
colnames = ['%s.%s' % (f.tablename, f.name)
|
||||
for f in extracted_fields]
|
||||
data = self._adapter.parse(
|
||||
data, fields=extracted_fields, colnames=colnames)
|
||||
@@ -7498,7 +7498,7 @@ class Table(dict):
|
||||
'value must be a dictionary: %s' % value
|
||||
dict.__setitem__(self, str(key), value)
|
||||
|
||||
def __getattr__(self, key):
|
||||
def __getattr__(self, key):
|
||||
return self[key]
|
||||
|
||||
def __delitem__(self, key):
|
||||
@@ -9153,3 +9153,4 @@ if __name__ == '__main__':
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -192,3 +192,4 @@ gluon.main.global_settings.debugging = True
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -78,3 +78,4 @@ def decoder(buffer):
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -397,3 +397,4 @@ def abspath(*relpath, **base):
|
||||
return os.path.join(global_settings.applications_parent, path)
|
||||
|
||||
|
||||
|
||||
|
||||
+2
-1
@@ -101,7 +101,7 @@ class Request(Storage):
|
||||
self.is_https = False
|
||||
self.is_local = False
|
||||
self.global_settings = settings.global_settings
|
||||
|
||||
|
||||
def compute_uuid(self):
|
||||
self.uuid = '%s/%s.%s.%s' % (
|
||||
self.application,
|
||||
@@ -691,3 +691,4 @@ class Session(Storage):
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -348,3 +348,4 @@ if __name__ == '__main__':
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
+2
-1
@@ -962,7 +962,7 @@ class DIV(XmlComponent):
|
||||
>>> for c in a.elements('input, select, textarea'): c['_disabled'] = 'disabled'
|
||||
>>> a.xml()
|
||||
'<form action="" enctype="multipart/form-data" method="post"><input disabled="disabled" type="text" /><select disabled="disabled"><option value="0">0</option></select><textarea cols="40" disabled="disabled" rows="10"></textarea></form>'
|
||||
|
||||
|
||||
Elements that are matched can also be replaced or removed by specifying
|
||||
a "replace" argument (note, a list of the original matching elements
|
||||
is still returned as usual).
|
||||
@@ -2503,3 +2503,4 @@ if __name__ == '__main__':
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -142,3 +142,4 @@ def redirect(location, how=303, client_side=False):
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -113,3 +113,4 @@ for module in base_modules + contributed_modules:
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -939,3 +939,4 @@ if __name__ == '__main__':
|
||||
doctest.testmod()
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -854,3 +854,4 @@ class HttpServer(object):
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -14,3 +14,4 @@ class MessageBoxHandler(logging.Handler):
|
||||
msg = self.format(record)
|
||||
tkMessageBox.showinfo('info1', msg)
|
||||
|
||||
|
||||
|
||||
@@ -32,3 +32,4 @@ regex_extend = re.compile(\
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -343,3 +343,4 @@ def crondance(applications_parent, ctype='soft', startup=False, apps=None):
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -151,3 +151,4 @@ if __name__=='__main__':
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -1717,3 +1717,4 @@ ADAPTERS['all'] = reduce(lambda a,b:a.union(b),(x for x in ADAPTERS.values()))
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -308,3 +308,4 @@ def snapshot(info=None, context=5, code=None, environment=None):
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
+2
-1
@@ -476,7 +476,7 @@ def load_routers(all_apps):
|
||||
def regex_uri(e, regexes, tag, default=None):
|
||||
"filter incoming URI against a list of regexes"
|
||||
path = e['PATH_INFO']
|
||||
host = e.get('http_host', e.get('SERVER_NAME','localhost')).lower()
|
||||
host = e.get('http_host', e.get('SERVER_NAME','localhost')).lower()
|
||||
i = host.find(':')
|
||||
if i > 0:
|
||||
host = host[:i]
|
||||
@@ -1311,3 +1311,4 @@ def get_effective_router(appname):
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -2085,3 +2085,4 @@ if __name__=='__main__':
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -228,3 +228,4 @@ def sanitize(text, permitted_tags=[
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -869,3 +869,4 @@ def main():
|
||||
|
||||
if __name__=='__main__':
|
||||
main()
|
||||
|
||||
|
||||
@@ -117,3 +117,4 @@ def rss(feed):
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -34,3 +34,4 @@ global_settings.is_jython = 'java' in sys.platform.lower() or \
|
||||
str(sys.copyright).find('Jython') > 0
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -431,3 +431,4 @@ if __name__ == '__main__':
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -9,3 +9,4 @@ from dal import DAL, Field, Table, Query, Set, Expression, Row, Rows, drivers, B
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
+2
-1
@@ -239,7 +239,7 @@ class ListWidget(StringWidget):
|
||||
else: _class = 'string'
|
||||
requires = field.requires if isinstance(field.requires, (IS_NOT_EMPTY, IS_LIST_OF)) else None
|
||||
attributes['_style'] = 'list-style:none'
|
||||
items=[LI(INPUT(_id=_id, _class=_class, _name=_name,
|
||||
items=[LI(INPUT(_id=_id, _class=_class, _name=_name,
|
||||
value=v, hideerror=True, requires=requires),
|
||||
**attributes) for v in value or ['']]
|
||||
script=SCRIPT("""
|
||||
@@ -2669,3 +2669,4 @@ class ExporterXML(ExportClass):
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
+3
-2
@@ -172,7 +172,7 @@ class Messages(Settings):
|
||||
|
||||
class FastStorage(dict):
|
||||
"""
|
||||
Eventually this should replace class Storage but causes memory leak
|
||||
Eventually this should replace class Storage but causes memory leak
|
||||
because of http://bugs.python.org/issue1469629
|
||||
|
||||
>>> s = FastStorage()
|
||||
@@ -205,7 +205,7 @@ class FastStorage(dict):
|
||||
>>> s['a']
|
||||
>>> s['b']
|
||||
"""
|
||||
def __init__(self, *args, **kwargs):
|
||||
def __init__(self, *args, **kwargs):
|
||||
dict.__init__(self, *args, **kwargs)
|
||||
self.__dict__ = self
|
||||
def __getattr__(self,key):
|
||||
@@ -269,3 +269,4 @@ if __name__ == '__main__':
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -112,3 +112,4 @@ def stream_file_or_304_or_206(
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
+3
-2
@@ -913,7 +913,7 @@ def render(content = "hello world",
|
||||
# Add it to the context so we can use it.
|
||||
if not 'NOESCAPE' in context:
|
||||
context['NOESCAPE'] = XML
|
||||
|
||||
|
||||
# save current response class
|
||||
if context and 'response' in context:
|
||||
old_response_body = context['response'].body
|
||||
@@ -926,7 +926,7 @@ def render(content = "hello world",
|
||||
if not content and not stream and not filename:
|
||||
raise SyntaxError, "Must specify a stream or filename or content"
|
||||
|
||||
# Here for legacy purposes, probably can be reduced to
|
||||
# Here for legacy purposes, probably can be reduced to
|
||||
# something more simple.
|
||||
close_stream = False
|
||||
if not stream:
|
||||
@@ -963,3 +963,4 @@ if __name__ == '__main__':
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
+12
-11
@@ -1410,9 +1410,9 @@ class Auth(object):
|
||||
passfield = settings.password_field
|
||||
extra_fields = settings.extra_fields.get(
|
||||
settings.table_user_name,[])+signature_list
|
||||
if username or settings.cas_provider:
|
||||
if username or settings.cas_provider:
|
||||
is_unique_username = \
|
||||
[IS_MATCH('[\w\.\-]+'),
|
||||
[IS_MATCH('[\w\.\-]+'),
|
||||
IS_NOT_IN_DB(db,'%s.username' % settings.table_user_name)]
|
||||
if not settings.username_case_sensitive:
|
||||
is_unique_username.insert(1,IS_LOWER())
|
||||
@@ -1584,7 +1584,7 @@ class Auth(object):
|
||||
'request_reset_password']
|
||||
from gluon.contrib.login_methods.cas_auth import CasAuth
|
||||
maps = settings.cas_maps
|
||||
if not maps:
|
||||
if not maps:
|
||||
table_user = self.table_user()
|
||||
maps = dict((name,lambda v,n=name:v.get(n,None)) for name in \
|
||||
table_user.fields if name!='id' \
|
||||
@@ -2476,7 +2476,7 @@ class Auth(object):
|
||||
separator=self.settings.label_separator
|
||||
)
|
||||
if captcha:
|
||||
addrow(form, captcha.label, captcha, captcha.comment, self.settings.formstyle,'captcha__row')
|
||||
addrow(form, captcha.label, captcha, captcha.comment, self.settings.formstyle,'captcha__row')
|
||||
if form.accepts(request, session,
|
||||
formname='reset_password', dbio=False,
|
||||
onvalidation=onvalidation,
|
||||
@@ -3133,7 +3133,7 @@ class Auth(object):
|
||||
archive_table_name,
|
||||
Field(current_record,table),
|
||||
*[field.clone(unique=False) for field in table])
|
||||
archive_table = table._db[archive_table_name]
|
||||
archive_table = table._db[archive_table_name]
|
||||
new_record = {current_record:form.vars.id}
|
||||
for fieldname in archive_table.fields:
|
||||
if not fieldname in ['id',current_record]:
|
||||
@@ -4484,7 +4484,7 @@ class Wiki(object):
|
||||
def __init__(self,auth,env=None,render='markmin',
|
||||
manage_permissions=False,force_prefix=''):
|
||||
self.env = env or {}
|
||||
self.env['component'] = Wiki.component
|
||||
self.env['component'] = Wiki.component
|
||||
if render == 'markmin': render=self.markmin_render
|
||||
self.auth = auth
|
||||
if self.auth.user:
|
||||
@@ -4536,7 +4536,7 @@ class Wiki(object):
|
||||
not 'wiki_editor' in auth.user_groups.values():
|
||||
group = db.auth_group(role='wiki_editor')
|
||||
gid = group.id if group else db.auth_group.insert(role='wiki_editor')
|
||||
auth.add_membership(gid)
|
||||
auth.add_membership(gid)
|
||||
# WIKI ACCESS POLICY
|
||||
def not_authorized(self,page=None):
|
||||
raise HTTP(401)
|
||||
@@ -4604,7 +4604,7 @@ class Wiki(object):
|
||||
|
||||
def fix_hostname(self,body):
|
||||
return body.replace('://HOSTNAME','://%s' % self.host)
|
||||
|
||||
|
||||
def read(self,slug):
|
||||
if slug in '_cloud': return self.cloud()
|
||||
elif slug in '_search': return self.search()
|
||||
@@ -4674,7 +4674,7 @@ class Wiki(object):
|
||||
|
||||
def editmedia(self,slug):
|
||||
auth = self.auth
|
||||
db = auth.db
|
||||
db = auth.db
|
||||
page = db.wiki_page(slug=slug)
|
||||
if not (page and self.can_edit(page)): return self.not_authorized(page)
|
||||
self.auth.db.wiki_media.id.represent = lambda id,row:\
|
||||
@@ -4739,9 +4739,9 @@ class Wiki(object):
|
||||
for match in regex.finditer(self.fix_hostname(menu_page.body)):
|
||||
base = match.group('base').replace(' ','')
|
||||
title = match.group('title')
|
||||
link = match.group('link')
|
||||
link = match.group('link')
|
||||
if link.startswith('@'):
|
||||
items = link[1:].split('/')
|
||||
items = link[2:].split('/')
|
||||
if len(items)>3:
|
||||
link = URL(a=items[0] or None,c=items[1] or None,f=items[2] or None, args=items[3:])
|
||||
parent = tree.get(base[1:],tree[''])
|
||||
@@ -4863,3 +4863,4 @@ if __name__ == '__main__':
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -654,3 +654,4 @@ if __name__ == '__main__':
|
||||
doctests()
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -186,3 +186,4 @@ def is_valid_ip_address(address):
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -3153,3 +3153,4 @@ if __name__ == '__main__':
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
+4
-3
@@ -929,10 +929,10 @@ def console():
|
||||
scheduler.append(opt.split(':'))
|
||||
options.scheduler = ','.join([app[0] for app in scheduler])
|
||||
options.scheduler_groups = scheduler
|
||||
|
||||
|
||||
if options.numthreads is not None and options.minthreads is None:
|
||||
options.minthreads = options.numthreads # legacy
|
||||
|
||||
options.minthreads = options.numthreads # legacy
|
||||
|
||||
if not options.cronjob:
|
||||
# If we have the applications package or if we should upgrade
|
||||
if not os.path.exists('applications/__init__.py'):
|
||||
@@ -1205,3 +1205,4 @@ end tell
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -172,3 +172,4 @@ if __name__ == '__main__':
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -25,3 +25,4 @@ def handler(request, response, methods):
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -37,3 +37,4 @@ if __name__=='__main__':
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -226,3 +226,4 @@ def handler(req):
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user