Răsfoiți Sursa

투표 기능 추가

잉여개발기 (SPDV) 5 ani în urmă
părinte
comite
de356acda9
12 a modificat fișierele cu 329 adăugiri și 27 ștergeri
  1. 22 1
      app.py
  2. 13 0
      language/en-US.json
  3. 34 22
      language/ko-KR.json
  4. 1 0
      route/main_other.py
  5. 6 1
      route/setting.py
  6. 6 1
      route/tool/func.py
  7. 41 0
      route/vote.py
  8. 62 0
      route/vote_add.py
  9. 29 0
      route/vote_close.py
  10. 47 0
      route/vote_end.py
  11. 66 0
      route/vote_select.py
  12. 2 2
      version.json

+ 22 - 1
app.py

@@ -146,7 +146,8 @@ create_data['scan'] = ['user', 'title', 'type']
 create_data['acl'] = ['title', 'decu', 'dis', 'view', 'why']
 create_data['inter'] = ['title', 'link', 'icon']
 create_data['html_filter'] = ['html', 'kind', 'plus']
-create_data['oauth_conn'] = ['provider', 'wiki_id', 'sns_id', 'name', 'picture']
+create_data['vote'] = ['name', 'id', 'subject', 'data', 'user', 'type', 'acl']
+# create_data['oauth_conn'] = ['provider', 'wiki_id', 'sns_id', 'name', 'picture']
 for i in create_data:
     try:
         curs.execute(db_change('select test from ' + i + ' limit 1'))
@@ -634,6 +635,26 @@ def application_submitted():
 def applications():
     return applications_2(conn)
 
+@app.route('/vote/<num>', methods=['POST', 'GET'])
+def vote_select(num = '1'):
+    return vote_select_2(conn, num)
+
+@app.route('/end_vote/<num>')
+def vote_end(num = '1'):
+    return vote_end_2(conn, num)
+
+@app.route('/close_vote/<num>')
+def vote_close(num = '1'):
+    return vote_close_2(conn, num)
+
+@app.route('/vote')
+def vote():
+    return vote_2(conn)
+
+@app.route('/add_vote', methods=['POST', 'GET'])
+def vote_add():
+    return vote_add_2(conn)
+
 # API
 @app.route('/api/w/<everything:name>', methods=['POST', 'GET'])
 def api_w(name = ''):

+ 13 - 0
language/en-US.json

@@ -101,6 +101,7 @@
         "extension" : "Extension",
         "empty" : "Empty",
         "domain" : "Domain",
+        "result" : "Result",
         "_comment_1.1_" : "Time",
             "second" : "Second(s)",
             "hour" : "Hour(s)",
@@ -346,6 +347,18 @@
             "approve_or_decline": "Approve or reject",
             "no_applications_now" : "There are no applications.",
             "approval_requirement_disabled": "Approval requirement is disabled now. You can enable this feature on settings",
+        "_comment_2.8_" : "Vote",
+            "vote_list" : "Vote list(s)",
+            "add_vote" : "Add vote",
+            "open_vote" : "Public vote",
+            "not_open_vote" : "Private vote",
+            "close_vote_list" : "Closed vote list(s)",
+            "open_vote_list" : "Open vote list(s)",
+            "vote" : "Vote",
+            "result_vote" : "Result of a vote",
+            "1_line_1_q" : "1 option per line.",
+            "close_vote" : "Close vote",
+            "re_open_vote" : "Reopen vote",
     "_comment_3_" : "Long",
         "application_submitted": "Applicatied successfully for registration",
         "waiting_for_approval": "Application for registration has been made successfully. Please wait for approval by administrators.",

+ 34 - 22
language/ko-KR.json

@@ -355,26 +355,38 @@
     "ban_acl": "차단된 사용자 포함",
     "ban_admin_acl": "차단된 사용자 및 관리자",
     "topic_name_change": "토론 제목 변경",
-    "topic_acl_setting" : "토론 ACL 설정",
-    "topic_acl" : "토론 ACL",
-    "main_skin_set" : "기본 스킨 설정",
-    "image_file_list" : "이미지 파일 목록",
-    "many_upload_acl" : "다중 파일 업로드 ACL",
-    "reset_backlink" : "역링크 초기화",
-    "link_in_this" : "이 문서의 링크",
-    "star_doc" : "관심 문서",
-    "add_star_doc" : "관심 문서 추가",
-    "enter_html" : "HTML을 입력하세요.",
-    "exp_edit_conflict" : "편집 충돌 발생",
-    "backup_where" : "백업 위치",
-    "empty" : "빈칸",
-    "email_send_error" : "이메일 전송이 실패했습니다.",
-    "get_sitemap" : "sitemap.xml 만들거나 갱신하기",
-    "same_ip_exist" : "동일한 아이피가 존재합니다.",
-    "restart_fail_error" : "재시작이 실패했습니다. 수동 재시작을 이용해주세요.",
-    "domain" : "도메인",
-    "before_acl" : "이 문서를 이전에 편집한 적 있는 사람만",
-    "30_day_acl" : "가입 후 30일이 지난 가입자만",
-    "simple_check" : "간편 검사",
-    "add_user" : "계정 추가"
+    "topic_acl_setting": "토론 ACL 설정",
+    "topic_acl": "토론 ACL",
+    "main_skin_set": "기본 스킨 설정",
+    "image_file_list": "이미지 파일 목록",
+    "many_upload_acl": "다중 파일 업로드 ACL",
+    "reset_backlink": "역링크 초기화",
+    "link_in_this": "이 문서의 링크",
+    "star_doc": "관심 문서",
+    "add_star_doc": "관심 문서 추가",
+    "enter_html": "HTML을 입력하세요.",
+    "exp_edit_conflict": "편집 충돌 발생",
+    "backup_where": "백업 위치",
+    "empty": "빈칸",
+    "email_send_error": "이메일 전송이 실패했습니다.",
+    "get_sitemap": "sitemap.xml 만들거나 갱신하기",
+    "same_ip_exist": "동일한 아이피가 존재합니다.",
+    "restart_fail_error": "재시작이 실패했습니다. 수동 재시작을 이용해주세요.",
+    "domain": "도메인",
+    "before_acl": "이 문서를 이전에 편집한 적 있는 사람만",
+    "30_day_acl": "가입 후 30일이 지난 가입자만",
+    "simple_check": "간편 검사",
+    "add_user": "계정 추가",
+    "result": "결과",
+    "vote_list": "투표 목록",
+    "add_vote": "투표 추가",
+    "open_vote": "공개 투표",
+    "not_open_vote": "비밀 투표",
+    "close_vote_list": "닫힌 투표 목록",
+    "vote": "투표",
+    "result_vote": "투표 결과",
+    "1_line_1_q": "1줄당 1개의 선택지를 쓰세요.",
+    "open_vote_list" : "열린 투표 목록",
+    "close_vote" : "투표 닫기",
+    "re_open_vote" : "투표 다시 열기"
 }

+ 1 - 0
route/main_other.py

@@ -24,6 +24,7 @@ def main_other_2(conn):
                 <li><a href="/admin_log">''' + load_lang('authority_use_list') + '''</a></li>
                 <li><a href="/old_page">''' + load_lang('old_page') + '''</a></li>
                 <li><a href="/image_file_list">''' + load_lang('image_file_list') + '''</a></li>
+                <li><a href="/vote">''' + load_lang('vote_list') + '''</a></li>
             </ul>
             <br>
             <h2>''' + load_lang('other') + '''</h2>

+ 6 - 1
route/setting.py

@@ -573,7 +573,8 @@ def setting_2(conn, num, db_set):
             2 : 'discussion',
             3 : 'upload_acl',
             4 : 'all_view_acl',
-            5 : 'many_upload_acl'
+            5 : 'many_upload_acl',
+            6 : 'vote_acl'
         }
 
         if flask.request.method == 'POST':
@@ -649,6 +650,10 @@ def setting_2(conn, num, db_set):
                         <hr class="main_hr">
                         <select ''' + disable + ''' name="many_upload_acl">''' + acl_div[4] + '''</select>
                         <hr class="main_hr">
+                        <span>''' + load_lang('vote_acl') + '''</span>
+                        <hr class="main_hr">
+                        <select ''' + disable + ''' name="vote_acl">''' + acl_div[5] + '''</select>
+                        <hr class="main_hr">
                         <button id="save" type="submit">''' + load_lang('save') + '''</button>
                     </form>
                 ''',

+ 6 - 1
route/tool/func.py

@@ -884,7 +884,7 @@ def acl_check(name = 'test', tool = '', topic_num = '1'):
             name = name[0][0] if name else 'test'
         
         end = 3
-    elif tool == 'render' or tool == '':
+    elif tool == 'render' or tool == '' or tool == 'vote':
         if tool == '' and acl_check(name, 'render') == 1:
             return 1
 
@@ -917,6 +917,11 @@ def acl_check(name = 'test', tool = '', topic_num = '1'):
             curs.execute(db_change("select data from other where name = 'many_upload_acl'"))
 
             num = 5
+        elif tool == 'vote':
+            if i == 0:
+                curs.execute(db_change('select acl from vote where id = ? and user = ""'), [topic_num])
+            else:
+                curs.execute(db_change('select data from other where name = "vote_acl"'))
         else:
             # tool == 'render'
             if i == 0:

+ 41 - 0
route/vote.py

@@ -0,0 +1,41 @@
+from .tool.func import *
+
+def vote_2(conn):
+    curs = conn.cursor()
+
+    sql_num_1 = int(number_check(flask.request.args.get('num', '1')))
+    sql_num = (sql_num_1 * 50 - 50) if sql_num_1 * 50 > 0 else 0
+
+    data = ''
+    if flask.request.args.get('close', 'n') == 'n':
+        data += '<a href="/vote?close=y">(' + load_lang('close_vote_list') + ')</a>'
+        sub = 0
+        curs.execute(db_change('select name, id, type from vote where type = "open" or type = "n_open" limit ?, 50'), [sql_num])
+    else:
+        data += '<a href="/vote">(' + load_lang('open_vote_list') + ')</a>'
+        sub = '(' + load_lang('closed') + ')'
+        curs.execute(db_change('select name, id, type from vote where type = "close" or type = "n_close" limit ?, 50'), [sql_num])
+
+    data += '<ul>'
+
+    data_list = curs.fetchall()
+    for i in data_list:
+        if flask.request.args.get('close', 'n') == 'n':
+            open_select = load_lang('open_vote') if i[2] == 'open' else load_lang('not_open_vote')
+        else:
+            open_select = load_lang('open_vote') if i[2] == 'close' else load_lang('not_open_vote')
+
+        data += '<li><a href="/vote/' + i[1] + '">' + html.escape(i[0]) + ' (' + open_select + ')</a></li>'
+
+    data += '</ul>'
+    if flask.request.args.get('close', 'n') == 'n':
+        data += ('<a href="/add_vote">(' + load_lang('add_vote') + ')</a>') if admin_check() == 1 else ''
+        data += next_fix('/vote?num=', sql_num_1, data_list)
+    else:
+        data += next_fix('/vote?close=y&num=', sql_num_1, data_list)
+
+    return easy_minify(flask.render_template(skin_check(),
+        imp = [load_lang('vote_list'), wiki_set(), custom(), other2([sub, 0])],
+        data = data,
+        menu = [['other', load_lang('return')]]
+    ))

+ 62 - 0
route/vote_add.py

@@ -0,0 +1,62 @@
+from .tool.func import *
+
+def vote_add_2(conn):
+    curs = conn.cursor()
+
+    if admin_check() != 1:
+        return re_error('/ban')
+
+    if flask.request.method == 'POST':
+        vote_data = flask.request.form.get('data', 'test\ntest_2')
+        if vote_data.count('\n') < 1:
+            return re_error('/ban')
+
+        curs.execute(db_change('select id from vote order by id + 0 desc limit 1'))
+        id_data = curs.fetchall()
+        id_data = str((int(id_data[0][0]) + 1) if id_data else 1)
+
+        admin_check(None, 'add vote ' + id_data)
+
+        if flask.request.form.get('open_select', 'N') == 'Y':
+            open_data = 'open'
+        else:
+            open_data = 'n_open'
+
+        curs.execute(db_change("insert into vote (name, id, subject, data, user, type, acl) values (?, ?, ?, ?, '', ?, ?)"), [
+            flask.request.form.get('name', 'test'),
+            id_data,
+            flask.request.form.get('subject', 'test'),
+            flask.request.form.get('data', 'test'),
+            open_data,
+            flask.request.form.get('acl_select', '')
+        ])
+        conn.commit()
+
+        return redirect('/vote')
+    else:
+        acl_data = '<select name="acl_select">'
+        acl_list = get_acl_list()
+        for data_list in acl_list:
+            acl_data += '<option value="' + data_list + '">' + (data_list if data_list != '' else 'normal') + '</option>'
+
+        acl_data += '</select>'
+
+        return easy_minify(flask.render_template(skin_check(),
+            imp = [load_lang('add_vote'), wiki_set(), custom(), other2([0, 0])],
+            data = '' + \
+                '<form method="post">' + \
+                    '<input name="name" placeholder="' + load_lang('name') + '">' + \
+                    '<hr class="main_hr">' + \
+                    '<textarea rows="3" name="subject" placeholder="' + load_lang('explanation') + '"></textarea>' + \
+                    '<hr class="main_hr">' + \
+                    '<textarea rows="10" name="data" placeholder="' + load_lang('1_line_1_q') + '"></textarea>' + \
+                    '<hr class="main_hr">' + \
+                    '<input type="checkbox" value="Y" name="open_select"> ' + load_lang('open_vote') + \
+                    '<h2>' + load_lang('acl') + '</h2>' + \
+                    acl_data + ' <a href="/acl/TEST#exp">(' + load_lang('explanation') + ')</a>' + \
+                    '<hr class="main_hr">' + \
+                    '<button type="submit">' + load_lang('send') + '</buttom>' + \
+                '</form>' + \
+            '',
+            menu = [['vote', load_lang('return')]]
+        ))

+ 29 - 0
route/vote_close.py

@@ -0,0 +1,29 @@
+from .tool.func import *
+
+def vote_close_2(conn, num):
+    curs = conn.cursor()
+
+    if admin_check() != 1:
+        return re_error('/ban')
+
+    curs.execute(db_change('select type from vote where id = ? and user = ""'), [num])
+    data_list = curs.fetchall()
+    if not data_list:
+        return redirect('/vote')
+        
+    if data_list[0][0] == 'close':
+        type_set = 'open'
+    elif data_list[0][0] == 'n_close':
+        type_set = 'n_open'
+    elif data_list[0][0] == 'open':
+        type_set = 'close'
+    else:
+        type_set = 'n_close'
+        
+    curs.execute(db_change("update vote set type = ? where user = '' and id = ?"), [type_set, num])
+    conn.commit()
+
+    if data_list[0][0] == 'close' or data_list[0][0] == 'n_close':
+        return redirect('/vote')
+    else:
+        return redirect('/vote?close=y')

+ 47 - 0
route/vote_end.py

@@ -0,0 +1,47 @@
+from .tool.func import *
+
+def vote_end_2(conn, num):
+    curs = conn.cursor()
+
+    curs.execute(db_change('select name, subject, data, type from vote where id = ? and user = ""'), [num])
+    data_list = curs.fetchall()
+    if not data_list:
+        return redirect('/vote')
+
+    data = '' + \
+        '<h2>' + data_list[0][0] + '</h2>' + \
+        '<b>' + data_list[0][1] + '</b>' + \
+    ''
+
+    if admin_check() == 1:
+        if data_list[0][3] == 'open' or data_list[0][3] == 'n_open':
+            data += '' + \
+                '<hr class="main_hr">' + \
+                '<a href="/close_vote/' + num + '">(' + load_lang('close_vote') + ')</a>' + \
+            ''
+        else:
+            data += '' + \
+                '<hr class="main_hr">' + \
+                '<a href="/close_vote/' + num + '">(' + load_lang('re_open_vote') + ')</a>' + \
+            ''
+
+    vote_data = re.findall(r'([^\n]+)', data_list[0][2].replace('\r\n', '\n'))
+    for i in range(0, len(vote_data)):
+        data += '<h2>' + vote_data[i] + '</h2>'
+        data += '<ul>'
+        
+        curs.execute(db_change('select user from vote where id = ? and user != "" and data = ?'), [num, str(i)])
+        data_list_2 = curs.fetchall()
+        if data_list[0][3] == 'open' or data_list[0][3] == 'close':
+            all_ip = ip_pas([j[0] for j in data_list_2])
+            for j in data_list_2:
+                data += '<li>' + all_ip[j[0]] + '</li>'
+
+        data += '<li>' + load_lang('result') + ' : ' + str(len(data_list_2)) + '</li>'
+        data += '</ul>'
+
+    return easy_minify(flask.render_template(skin_check(),
+        imp = [load_lang('result_vote'), wiki_set(), custom(), other2([0, 0])],
+        data = data,
+        menu = [['vote', load_lang('return')]]
+    ))

+ 66 - 0
route/vote_select.py

@@ -0,0 +1,66 @@
+from .tool.func import *
+
+def vote_select_2(conn, num):
+    curs = conn.cursor()
+
+    curs.execute(db_change('select name, subject, data, type from vote where id = ? and user = ""'), [num])
+    data_list = curs.fetchall()
+    if not data_list:
+        return redirect('/vote')
+
+    if data_list[0][3] == 'close' or data_list[0][3] == 'n_close':
+        return redirect('/end_vote/' + num)
+
+    if acl_check('', 'vote', num) == 1:
+        return redirect('/end_vote/' + num)
+
+    curs.execute(db_change('select user from vote where id = ? and user = ?'), [num, ip_check()])
+    if curs.fetchall():
+        return redirect('/end_vote/' + num)
+
+    vote_data = re.findall(r'([^\n]+)', data_list[0][2].replace('\r\n', '\n'))
+
+    if flask.request.method == 'POST':
+        try:
+            vaild_check = int(flask.request.form.get('vote_data', '0'))
+        except:
+            return redirect('/vote/' + num)
+
+        if len(vote_data) - 1 < vaild_check:
+            return redirect('/vote/' + num)
+
+        curs.execute(db_change("insert into vote (name, id, subject, data, user, type) values ('', ?, '', ?, ?, 'select')"), [
+            num,
+            str(vaild_check),
+            ip_check()
+        ])
+        conn.commit()
+
+        return redirect('/end_vote/' + num)
+    else:
+        data = '' + \
+            '<h2>' + data_list[0][0] + '</h2>' + \
+            '<b>' + data_list[0][1] + '</b>' + \
+            '<hr class="main_hr">' + \
+        ''
+
+        select_data = '<select name="vote_data">'
+        line_num = 0
+        for i in vote_data:
+            select_data += '<option value="' + str(line_num) + '">' + i + '</option>'
+            line_num += 1
+
+        select_data += '</select>'
+        data += '' + \
+            '<form method="post">' + \
+                select_data + \
+                '<hr class="main_hr">' + \
+                '<button type="submit">' + load_lang('send') + '</buttom>' + \
+            '</form>' + \
+        ''
+
+        return easy_minify(flask.render_template(skin_check(),
+            imp = [load_lang('vote'), wiki_set(), custom(), other2([0, 0])],
+            data = data,
+            menu = [['vote', load_lang('return')], ['end_vote/' + num, load_lang('result')]]
+        ))

+ 2 - 2
version.json

@@ -1,7 +1,7 @@
 {
     "master" : {
-        "r_ver" : "v3.2.0-master-15",
-        "c_ver" : "3200900",
+        "r_ver" : "v3.2.0-master-16",
+        "c_ver" : "3201601",
         "s_ver" : "9"
     }, "stable" : {
         "r_ver" : "v3.2.0-stable-11",