www/members/inactive.cgi (208 lines of code) (raw):

#!/usr/bin/env ruby PAGETITLE = "Your Member Meeting Attendance Status and Update Tool" # Wvisible:meeting $LOAD_PATH.unshift '/srv/whimsy/lib' require 'whimsy/asf' require 'wunderbar/bootstrap' require 'date' require 'json' require 'tmpdir' require 'whimsy/asf/meeting-util' # produce HTML _html do _head_ do _style :system _style %{ div.status, .status form, pre.issue {margin-left: 16px} .btn {margin: 4px} form {margin-bottom: 1em} .transcript {margin: 0 16px} .transcript pre {border: none; line-height: 0} pre._hilite {background-color: yellow} form p {margin-top: 1em} form {display: inline-block} textarea {width: 100%; height: 8em} textarea:disabled {background-color: #EEEEEE} div.alert {background-color: yellow; border: solid 2px red; padding-top: 0} } end _body? do MEETINGS = ASF::SVN['Meetings'] attendance = ASF::MeetingUtil.get_attendance(MEETINGS) latest = ASF::MeetingUtil.get_latest(MEETINGS) @user ||= $USER @meetingsMissed = (@meetingsMissed || 3).to_i # Allow a non-participating member to post a request to go emeritus if _.post? and @status == 'go emeritus' and $USER == @user # stub out roster functions require 'mail' class Committer; def self.serialize(*args); end; end def _committer(*args); end def env.user; $USER; end def env.password; $PASSWORD; end # issue request @action = 'request_emeritus' @userid = $USER eval IO.read(File.expand_path('../roster/views/actions/memstat.json.rb', __dir__)) # Provide visual feedback _div.alert do _h3 'Emeritus request submitted' _ul do _li 'Check your email for confirmation.' _li 'Your status will be updated on Whimsy within 10 minutes.' end end end # Get live data of members' attendance or current proxies submitted tracker = ASF::MeetingUtil.tracker(@meetingsMissed) # determine user's name as found in members.txt name = ASF::Member.find_text_by_id(@user).to_s.split("\n").first matrix = attendance['matrix'][name] # defaults for active users tracker[@user] ||= { 'missed' => 0, 'status' => 'active - attended meetings recently' } active = (tracker[@user]['missed'] < @meetingsMissed) _whimsy_body( title: PAGETITLE, subtitle: active ? 'Your Attendance Status' : 'Poll Of Inactive Members', relatedtitle: 'More About Meetings', related: { 'https://www.apache.org/foundation/governance/meetings' => 'How Meetings & Voting Works', '/members/proxy' => 'Assign A Proxy For Next Meeting', '/members/non-participants' => 'Members Not Participating', ASF::SVN.svnpath!('foundation','members.txt') => 'See Official Members.txt File', ASF::MeetingUtil::RECORDS => 'Official Past Meeting Records' }, helpblock: -> { _p "This page shows your personal attendance record at past Member's meetings, as of meeting #{latest}." _p %{ Inactive members (only) will see a button to request a proxy for the next meeting, and a second button that they can use to request to go emeritus. They also will see the text of an issue that will be placed before the membership for a vote should they not take either of these two options. } _p do _b %{ N.B. Attendance details for the June 2022 meeting were only added recently. Unfortunately this was only discovered after an email was sent to members. Apologies to those of you who received an email in error. } end } ) do member_status = ASF::Person.find(@user).asf_member? _p_ do if member_status != true _span "#{name}, your current membership status is: " _code member_status else _span "#{name}, your current meeting attendance status is: " _code tracker[@user]['status'] end end if active and member_status == true att = miss = 0 if !matrix.nil? matrix.each do |date, status| if %w(A V P).include? status att += 1 elsif date != 'active' miss += 1 end end end if 0 == miss && 0 == att _p.text_success "No attendance for Member's meetings found yet" else _p.text_success "Great! Thanks for attending Member's meetings recently! Overall attends: #{att} Non-attends: #{miss}" if 0 == miss _p.text_success "WOW! 100% attendance rate - thanks!" end end end if not active _p.alert.alert_warning "Dear #{name}, You have missed the last " + tracker[@user]['missed'].to_s + " meetings." _div.status do wrap = 80 issue_text = `#{MEETINGS}/whimsy-tools/issue-description.py #{name.inspect} #{ASF::SVN['foundation']}`. gsub(/(.{1,#{wrap}})( +|$\n?)|(.{1,#{wrap}})/, "\\1\\3\n") if Dir.exist? File.join(latest, 'issues') _p 'Based on this status, the following text has been placed before the membership as a vote' else _p %{ Based on this status, the following text will be placed before the membership as a vote UNLESS you either assign a proxy for the next meeting or voluntarily request a conversion to emeritus status. } end _pre.issue issue_text _p 'Update your status (if you are inactive):' _form method: 'get', action: 'proxy' do _button.btn.btn_success 'Request a proxy', name: 'status', value: 'request proxy', disabled: $USER != @user || tracker[@user]['status'] == 'Proxy received' end _form method: 'post' do _button.btn.btn_warning 'I would like to go emeritus', name: 'status', value: 'go emeritus', disabled: $USER != @user || tracker[@user]['status'] == 'Emeritus request received' end _p_ %{ If you haven't attended or voted in meetings recently, please consider participating, at least by proxy, in the upcoming membership meeting. Assigning a proxy does NOT prevent you from attending meetings. Normally, your proxy will just be at the meeting to mark your attendance. You will still get any vote emails yourself. Remember that voting at a meeting also counts for attendance. } end end _h1_ 'Your Attendance history', id: 'attendance' if not name _p.alert.alert_danger "#{@user} not found in members.txt" elsif not matrix _p.alert.alert_danger "#{name} not found in attendance matrix" else _table.table.table_sm style: 'margin: 0 24px; width: auto' do _thead do _tr do _th 'Date' _th 'Status' end end matrix.sort.reverse.each do |date, status| next if status == ' ' next if date == 'active' color = 'bg-danger' color = 'bg-warning' if %w(e).include? status color = 'bg-success' if %w(A V P).include? status _tr_ class: color do _td do _a date, href: ASF::SVN.svnpath!('Meetings') + date end case status when 'A' _td 'Attended' when 'V' _td 'Voted but did not attend' when 'P' _td 'Attended via proxy' when '-' _td 'Did not attend' when 'e' _td 'Went emeritus' else _td status end end end end end end end end