diff --git a/helios/security.py b/helios/security.py
index 1a5a78df6e1ae875f2e0dd5b7379658dac8e3c52..971499e7c18fe50e268591a39aea9cf0cacc61f5 100644
--- a/helios/security.py
+++ b/helios/security.py
@@ -187,7 +187,7 @@ def can_create_election(request):
   if helios.ADMIN_ONLY:
     return user.admin_p
   else:
-    return user != None
+    return user.can_create_election()
   
 def user_can_feature_election(user, election):
   if not user:
diff --git a/helios_auth/auth_systems/cas.py b/helios_auth/auth_systems/cas.py
index 139a6d7c5ab0905e9d276cccdfd0f874a3719b4f..8202ad262712f527b8f8896b02b7a2b47b445917 100644
--- a/helios_auth/auth_systems/cas.py
+++ b/helios_auth/auth_systems/cas.py
@@ -242,3 +242,11 @@ def eligibility_category_id(constraint):
 
 def pretty_eligibility(constraint):
   return "Members of the Class of %s" % constraint['year']
+
+
+#
+# Election Creation
+#
+
+def can_create_election(user_id, user_info):
+  return True
diff --git a/helios_auth/auth_systems/clever.py b/helios_auth/auth_systems/clever.py
index 08456f562811743900f8146bcab89eec65467c0a..dcd52d0e522b4bf2039a6d5752dca26090eefa9c 100644
--- a/helios_auth/auth_systems/clever.py
+++ b/helios_auth/auth_systems/clever.py
@@ -71,13 +71,14 @@ def get_user_info_after_auth(request):
   user_name = "%s %s" % (response['data']['name']['first'], response['data']['name']['last'])
   user_type = response['type']
   user_district = response['data']['district']
+  user_grade = response['data'].get('grade', None)
 
   print content
   
   # watch out, response also contains email addresses, but not sure whether thsoe are verified or not
   # so for email address we will only look at the id_token
   
-  return {'type' : 'clever', 'user_id': user_id, 'name': user_name , 'info': {"district": user_district, "type": user_type}, 'token': {'access_token': access_token}}
+  return {'type' : 'clever', 'user_id': user_id, 'name': user_name , 'info': {"district": user_district, "type": user_type, "grade": user_grade}, 'token': {'access_token': access_token}}
     
 def do_logout(user):
   """
@@ -96,9 +97,40 @@ def send_message(user_id, name, user_info, subject, body):
   send email to google users. user_id is the email for google.
   """
   pass
+
+#
+# eligibility
+#
+
+def check_constraint(constraint, user):
+  if not user.info.has_key('grade'):
+    return False
+  return constraint['grade'] == user.info['grade']
+
+def generate_constraint(category, user):
+  """
+  generate the proper basic data structure to express a constraint
+  based on the category string
+  """
+  return {'grade': category}
+
+def list_categories(user):
+  return [{"id": str(g), "name": "Grade %d" % g} for g in range(3,13)]
   
-def check_constraint(constraint, user_info):
+def eligibility_category_id(constraint):
+  return constraint['grade']
+
+def pretty_eligibility(constraint):
+  return "Grade %s" % constraint['grade']
+  
+
+
+#
+# Election Creation
+#
+
+def can_create_election(user_id, user_info):
   """
-  for eligibility
+  Teachers only for now
   """
-  pass
+  return user_info['type'] == 'teacher'
diff --git a/helios_auth/auth_systems/facebook.py b/helios_auth/auth_systems/facebook.py
index d510ced0caa2417b04f83941aeb0a2fc7517f5a5..179013584b0fad8d7087bd22af6ac56bb99de896 100644
--- a/helios_auth/auth_systems/facebook.py
+++ b/helios_auth/auth_systems/facebook.py
@@ -116,3 +116,10 @@ def eligibility_category_id(constraint):
 
 def pretty_eligibility(constraint):
   return "Facebook users who are members of the \"%s\" group" % constraint['group']['name']
+
+#
+# Election Creation
+#
+
+def can_create_election(user_id, user_info):
+  return True
diff --git a/helios_auth/auth_systems/google.py b/helios_auth/auth_systems/google.py
index 00a6bb7180ffab81d5b5bf56f65f3b5b08b1d664..2bdd38c7c0d093bd349a582946dfb31fdd7a57e7 100644
--- a/helios_auth/auth_systems/google.py
+++ b/helios_auth/auth_systems/google.py
@@ -82,3 +82,11 @@ def check_constraint(constraint, user_info):
   for eligibility
   """
   pass
+
+
+#
+# Election Creation
+#
+
+def can_create_election(user_id, user_info):
+  return True
diff --git a/helios_auth/auth_systems/linkedin.py b/helios_auth/auth_systems/linkedin.py
index 69e3e9a083b441b65c6d5fff9b810db6323df226..32b0033c14fc0c3277671470055d91dbd1271556 100644
--- a/helios_auth/auth_systems/linkedin.py
+++ b/helios_auth/auth_systems/linkedin.py
@@ -89,3 +89,10 @@ def send_notification(user_id, user_info, message):
   pass
 
 
+
+#
+# Election Creation
+#
+
+def can_create_election(user_id, user_info):
+  return True
diff --git a/helios_auth/auth_systems/live.py b/helios_auth/auth_systems/live.py
index 6a1b20eb42780964ebac1378cff80ba6ea97dd2c..9f34a2783198003f09a74abb1671d9630cf3895a 100644
--- a/helios_auth/auth_systems/live.py
+++ b/helios_auth/auth_systems/live.py
@@ -65,3 +65,11 @@ def update_status(user_id, user_info, token, message):
 
 def send_message(user_id, user_name, user_info, subject, body):
   pass
+
+
+#
+# Election Creation
+#
+
+def can_create_election(user_id, user_info):
+  return True
diff --git a/helios_auth/auth_systems/password.py b/helios_auth/auth_systems/password.py
index e39573e0200d0717adffe8f1d90939481d373e88..625b8650eca75ce3fd51c9fdebeb21ce05efbe22 100644
--- a/helios_auth/auth_systems/password.py
+++ b/helios_auth/auth_systems/password.py
@@ -117,3 +117,11 @@ def send_message(user_id, user_name, user_info, subject, body):
   email = user_id
   name = user_name or user_info.get('name', email)
   send_mail(subject, body, settings.SERVER_EMAIL, ["\"%s\" <%s>" % (name, email)], fail_silently=False)    
+
+
+#
+# Election Creation
+#
+
+def can_create_election(user_id, user_info):
+  return True
diff --git a/helios_auth/auth_systems/twitter.py b/helios_auth/auth_systems/twitter.py
index 343b555191bb0ee1877ec6f1fb02138ac874799c..9963f9121d42b3c53edaac0c128f67499d98c761 100644
--- a/helios_auth/auth_systems/twitter.py
+++ b/helios_auth/auth_systems/twitter.py
@@ -118,3 +118,10 @@ def follow_view(request):
     return HttpResponseRedirect(reverse(after_intervention))
 
 
+
+#
+# Election Creation
+#
+
+def can_create_election(user_id, user_info):
+  return True
diff --git a/helios_auth/auth_systems/yahoo.py b/helios_auth/auth_systems/yahoo.py
index dc29ab75ccb5a08b29a2aab1c806d9d647d496f6..16bc0343cd40b78386a95fb0279c05c02b23f317 100644
--- a/helios_auth/auth_systems/yahoo.py
+++ b/helios_auth/auth_systems/yahoo.py
@@ -52,3 +52,11 @@ def check_constraint(constraint, user_info):
   for eligibility
   """
   pass
+
+
+#
+# Election Creation
+#
+
+def can_create_election(user_id, user_info):
+  return True
diff --git a/helios_auth/models.py b/helios_auth/models.py
index 5ec2adfbe8f150d87120560c6164865e362985a3..b9179958e5bbca1ad7d9eacc4c2264c020fecf4b 100644
--- a/helios_auth/models.py
+++ b/helios_auth/models.py
@@ -70,6 +70,16 @@ class User(models.Model):
 
     return AUTH_SYSTEMS[self.user_type].STATUS_UPDATES
 
+  def can_create_election(self):
+    """
+    Certain auth systems can choose to limit election creation
+    to certain users. 
+    """
+    if not AUTH_SYSTEMS.has_key(self.user_type):
+      return False
+    
+    return AUTH_SYSTEMS[self.user_type].can_create_election(self.user_id, self.info)
+
   def update_status_template(self):
     if not self.can_update_status():
       return None