def attendees(self, session, target_server='', api_token='', query='', message=''): target_url, target_host, remote_api_token = _format_import_params(target_server, api_token) results = {} if cherrypy.request.method == 'POST': if not remote_api_token: message = 'No API token given and could not find a token for: {}'.format(target_host) elif not target_url: message = 'Unrecognized hostname: {}'.format(target_server) if not message: try: uri = '{}/jsonrpc/'.format(target_url) service = ServerProxy(uri=uri, extra_headers={'X-Auth-Token': remote_api_token}) results = service.attendee.export(query=query) except Exception as ex: message = str(ex) attendees = results.get('attendees', []) for attendee in attendees: attendee['href'] = '{}/registration/form?id={}'.format(target_url, attendee['id']) if attendees: attendees_by_name_email = groupify(attendees, lambda a: ( a['first_name'].lower(), a['last_name'].lower(), Attendee.normalize_email(a['email']), )) filters = [ and_( func.lower(Attendee.first_name) == first, func.lower(Attendee.last_name) == last, Attendee.normalized_email == email, ) for first, last, email in attendees_by_name_email.keys() ] existing_attendees = session.query(Attendee).filter(or_(*filters)).all() for attendee in existing_attendees: existing_key = (attendee.first_name.lower(), attendee.last_name.lower(), attendee.normalized_email) attendees_by_name_email.pop(existing_key, {}) attendees = list(chain(*attendees_by_name_email.values())) else: existing_attendees = [] return { 'target_server': target_server, 'api_token': api_token, 'query': query, 'message': message, 'unknown_ids': results.get('unknown_ids', []), 'unknown_emails': results.get('unknown_emails', []), 'unknown_names': results.get('unknown_names', []), 'unknown_names_and_emails': results.get('unknown_names_and_emails', []), 'attendees': attendees, 'existing_attendees': existing_attendees, }
def import_attendees(self, session, target_server='', api_token='', query='', message=''): service, service_message, target_url = get_api_service_from_server(target_server, api_token) message = message or service_message attendees, existing_attendees, results = {}, {}, {} if service: try: results = service.attendee.export(query=query) except Exception as ex: message = str(ex) if cherrypy.request.method == 'POST' and not message: attendees = results.get('attendees', []) for attendee in attendees: attendee['href'] = '{}/registration/form?id={}'.format(target_url, attendee['id']) if attendees: attendees_by_name_email = groupify(attendees, lambda a: ( a['first_name'].lower(), a['last_name'].lower(), Attendee.normalize_email(a['email']), )) filters = [ and_( func.lower(Attendee.first_name) == first, func.lower(Attendee.last_name) == last, Attendee.normalized_email == email, ) for first, last, email in attendees_by_name_email.keys() ] existing_attendees = session.query(Attendee).filter(or_(*filters)).all() for attendee in existing_attendees: existing_key = (attendee.first_name.lower(), attendee.last_name.lower(), attendee.normalized_email) attendees_by_name_email.pop(existing_key, {}) attendees = list(chain(*attendees_by_name_email.values())) return { 'target_server': target_server, 'api_token': api_token, 'query': query, 'message': message, 'unknown_ids': results.get('unknown_ids', []), 'unknown_emails': results.get('unknown_emails', []), 'unknown_names': results.get('unknown_names', []), 'unknown_names_and_emails': results.get('unknown_names_and_emails', []), 'attendees': attendees, 'existing_attendees': existing_attendees, }
def staff(self, session, target_server='', api_token='', query='', message=''): target_url = _server_to_url(target_server) if cherrypy.request.method == 'POST': try: uri = '{}/jsonrpc/'.format(target_url) service = ServerProxy( uri=uri, extra_headers={'X-Auth-Token': api_token.strip()}) results = service.attendee.export(query=query) except Exception as ex: message = str(ex) results = {} else: results = {} attendees = results.get('attendees', []) for attendee in attendees: attendee['href'] = '{}/registration/form?id={}'.format( target_url, attendee['id']) if attendees: attendees_by_email = groupify( attendees, lambda a: Attendee.normalize_email(a['email'])) emails = list(attendees_by_email.keys()) existing_attendees = session.query(Attendee).filter( Attendee.normalized_email.in_(emails)).all() for attendee in existing_attendees: attendees_by_email.pop(attendee.normalized_email, {}) attendees = list(chain(*attendees_by_email.values())) else: existing_attendees = [] return { 'target_server': target_server, 'api_token': api_token, 'query': query, 'message': message, 'unknown_emails': results.get('unknown_emails', []), 'unknown_names': results.get('unknown_names', []), 'attendees': attendees, 'existing_attendees': existing_attendees, }
def export(self, query, full=False): """ Searches for attendees by either email, "first last" name, or "first last <email>" combinations. `query` should be a comma or newline separated list of email/name queries. Example: <pre>Merrium Webster, [email protected], John Doe <[email protected]></pre> Results are returned in the format expected by <a href="../import/staff">the staff importer</a>. """ _re_name_email = re.compile(r'^\s*(.*?)\s*<\s*(.*?@.*?)\s*>\s*$') _re_sep = re.compile(r'[\n,]') _re_whitespace = re.compile(r'\s+') queries = [s.strip() for s in _re_sep.split(normalize_newlines(query)) if s.strip()] names = dict() emails = dict() names_and_emails = dict() ids = set() for q in queries: if '@' in q: match = _re_name_email.match(q) if match: name = match.group(1) email = Attendee.normalize_email(match.group(2)) if name: first, last = (_re_whitespace.split(name.lower(), 1) + [''])[0:2] names_and_emails[(first, last, email)] = q else: emails[email] = q else: emails[Attendee.normalize_email(q)] = q elif q: try: ids.add(str(uuid.UUID(q))) except Exception: first, last = (_re_whitespace.split(q.lower(), 1) + [''])[0:2] names[(first, last)] = q with Session() as session: if full: options = [ subqueryload(Attendee.dept_memberships).subqueryload(DeptMembership.department), subqueryload(Attendee.dept_membership_requests).subqueryload(DeptMembershipRequest.department)] else: options = [] email_attendees = [] if emails: email_attendees = session.query(Attendee).filter(Attendee.normalized_email.in_(list(emails.keys()))) \ .options(*options).order_by(Attendee.email, Attendee.id).all() known_emails = set(a.normalized_email for a in email_attendees) unknown_emails = sorted([raw for normalized, raw in emails.items() if normalized not in known_emails]) name_attendees = [] if names: filters = [ and_(func.lower(Attendee.first_name) == first, func.lower(Attendee.last_name) == last) for first, last in names.keys()] name_attendees = session.query(Attendee).filter(or_(*filters)) \ .options(*options).order_by(Attendee.email, Attendee.id).all() known_names = set((a.first_name.lower(), a.last_name.lower()) for a in name_attendees) unknown_names = sorted([raw for normalized, raw in names.items() if normalized not in known_names]) name_and_email_attendees = [] if names_and_emails: filters = [ and_( func.lower(Attendee.first_name) == first, func.lower(Attendee.last_name) == last, Attendee.normalized_email == email) for first, last, email in names_and_emails.keys()] name_and_email_attendees = session.query(Attendee).filter(or_(*filters)) \ .options(*options).order_by(Attendee.email, Attendee.id).all() known_names_and_emails = set( (a.first_name.lower(), a.last_name.lower(), a.normalized_email) for a in name_and_email_attendees) unknown_names_and_emails = sorted([ raw for normalized, raw in names_and_emails.items() if normalized not in known_names_and_emails]) id_attendees = [] if ids: id_attendees = session.query(Attendee).filter(Attendee.id.in_(ids)) \ .options(*options).order_by(Attendee.email, Attendee.id).all() known_ids = set(str(a.id) for a in id_attendees) unknown_ids = sorted([i for i in ids if i not in known_ids]) seen = set() all_attendees = [ a for a in (id_attendees + email_attendees + name_attendees + name_and_email_attendees) if a.id not in seen and not seen.add(a.id)] fields = [ 'first_name', 'last_name', 'birthdate', 'email', 'zip_code', 'birthdate', 'international', 'ec_name', 'ec_phone', 'cellphone', 'badge_printed_name', 'found_how', 'comments', 'admin_notes', 'all_years', 'badge_status', 'badge_status_label', ] if full: fields.extend(['shirt']) attendees = [] for a in all_attendees: d = a.to_dict(fields) if full: assigned_depts = {} checklist_admin_depts = {} dept_head_depts = {} poc_depts = {} for membership in a.dept_memberships: assigned_depts[membership.department_id] = membership.department.name if membership.is_checklist_admin: checklist_admin_depts[membership.department_id] = membership.department.name if membership.is_dept_head: dept_head_depts[membership.department_id] = membership.department.name if membership.is_poc: poc_depts[membership.department_id] = membership.department.name d.update({ 'assigned_depts': assigned_depts, 'checklist_admin_depts': checklist_admin_depts, 'dept_head_depts': dept_head_depts, 'poc_depts': poc_depts, 'requested_depts': { (m.department_id if m.department_id else 'All'): (m.department.name if m.department_id else 'Anywhere') for m in a.dept_membership_requests}, }) attendees.append(d) return { 'unknown_ids': unknown_ids, 'unknown_emails': unknown_emails, 'unknown_names': unknown_names, 'unknown_names_and_emails': unknown_names_and_emails, 'attendees': attendees, }
def export(self, query, full=False): """ Searches for attendees by either email or first and last name. `query` should be a comma or newline separated list of emails and "first last" name combos. Results are returned in the format expected by <a href="../import/staff">the staff importer</a>. """ queries = [s.strip() for s in re.split('[\n,]', normalize_newlines(query)) if s.strip()] names = dict() emails = dict() ids = set() for q in queries: if '@' in q: emails[Attendee.normalize_email(q)] = q elif q: try: ids.add(str(uuid.UUID(q))) except Exception: first, _, last = [s.strip() for s in q.partition(' ')] names[q] = (first.lower(), last.lower()) with Session() as session: if full: options = [ subqueryload(Attendee.dept_memberships).subqueryload(DeptMembership.department), subqueryload(Attendee.dept_membership_requests).subqueryload(DeptMembershipRequest.department)] else: options = [] email_attendees = [] if emails: email_attendees = session.query(Attendee).filter(Attendee.normalized_email.in_(list(emails.keys()))) \ .options(*options).order_by(Attendee.email, Attendee.id).all() known_emails = set(a.normalized_email for a in email_attendees) unknown_emails = sorted([email for normalized, email in emails.items() if normalized not in known_emails]) name_attendees = [] if names: filters = [ and_(func.lower(Attendee.first_name) == n[0], func.lower(Attendee.last_name) == n[1]) for n in names.values()] name_attendees = session.query(Attendee).filter(or_(*filters)) \ .options(*options).order_by(Attendee.email, Attendee.id).all() id_attendees = [] if ids: id_attendees = session.query(Attendee).filter(Attendee.id.in_(ids)) \ .options(*options).order_by(Attendee.email, Attendee.id).all() known_names = set(a.full_name.lower() for a in name_attendees) unknown_names = sorted([full_name for full_name in names.keys() if full_name.lower() not in known_names]) seen = set() all_attendees = [ a for a in (id_attendees + email_attendees + name_attendees) if a.id not in seen and not seen.add(a.id)] fields = [ 'first_name', 'last_name', 'birthdate', 'email', 'zip_code', 'birthdate', 'international', 'ec_name', 'ec_phone', 'cellphone', 'badge_printed_name', 'found_how', 'comments', 'admin_notes', 'all_years', ] attendees = [] for a in all_attendees: d = a.to_dict(fields) if full: assigned_depts = {} checklist_admin_depts = {} dept_head_depts = {} poc_depts = {} for membership in a.dept_memberships: assigned_depts[membership.department_id] = membership.department.name if membership.is_checklist_admin: checklist_admin_depts[membership.department_id] = membership.department.name if membership.is_dept_head: dept_head_depts[membership.department_id] = membership.department.name if membership.is_poc: poc_depts[membership.department_id] = membership.department.name d.update({ 'assigned_depts': assigned_depts, 'checklist_admin_depts': checklist_admin_depts, 'dept_head_depts': dept_head_depts, 'poc_depts': poc_depts, 'requested_depts': { (m.department_id if m.department_id else 'All'): (m.department.name if m.department_id else 'Anywhere') for m in a.dept_membership_requests}, }) attendees.append(d) return { 'unknown_emails': unknown_emails, 'unknown_names': unknown_names, 'attendees': attendees, }