Description:
merge bootstrap back to algo
Commit status:
[Not Reviewed]
References:
merge algo
Comments:
0 Commit comments 0 Inline Comments
Unresolved TODOs:
There are no unresolved TODOs
Add another comment

r704:4afa0e9c66d2 - - 103 files changed: 1725 inserted, 816 deleted

@@ -0,0 +1,6
1 + #js for announcement
2 + $ ->
3 + $(document).ajaxError (event, jqxhr, settings, exception) ->
4 + if jqxhr.status
5 + alert 'We\'re sorry, but something went wrong (' + jqxhr.status + ')'
6 + return
new file 100644
new file 100644
new file 100644
@@ -0,0 +1,52
1 + $(document).on 'change', '.btn-file :file', ->
2 + input = $(this)
3 + numFiles = if input.get(0).files then input.get(0).files.length else 1
4 + label = input.val().replace(/\\/g, '/').replace(/.*\//, '')
5 + input.trigger 'fileselect', [
6 + numFiles
7 + label
8 + ]
9 + return
10 +
11 +
12 + # document ready
13 +
14 + $ ->
15 + $(".select2").select2()
16 + #$(".bootstrap-switch").bootstrapSwitch()
17 + #$(".bootstrap-toggle").bootstrapToggle()
18 + $('.btn-file :file').on 'fileselect', (event, numFiles, label) ->
19 + input = $(this).parents('.input-group').find(':text')
20 + log = if numFiles > 1 then numFiles + ' files selected' else label
21 + if input.length
22 + input.val log
23 + else
24 + if log
25 + alert log
26 + return
27 + $(".go-button").on 'click', (event) ->
28 + link = $(this).attr("data-source")
29 + url = $(link).val()
30 + if url
31 + window.location.href = url
32 + return
33 + $('.ajax-toggle').on 'click', (event) ->
34 + target = $(event.target)
35 + target.removeClass 'btn-default'
36 + target.removeClass 'btn-success'
37 + target.addClass 'btn-warning'
38 + target.text '...'
39 + return
40 +
41 +
42 + #ace editor
43 + if $("#editor").length > 0
44 + e = ace.edit("editor")
45 + e.setTheme('ace/theme/merbivore')
46 + e.getSession().setTabSize(2)
47 + e.getSession().setUseSoftTabs(true)
48 +
49 + #best in place
50 + jQuery(".best_in_place").best_in_place()
51 +
52 + return
new file 100644
new file 100644
new file 100644
new file 100644
new file 100644
new file 100644
new file 100644
new file 100644
@@ -0,0 +1,32
1 + # Place all the behaviors and hooks related to the matching controller here.
2 + # All this logic will automatically be available in application.js.
3 + # You can use CoffeeScript in this file: http://jashkenas.github.com/coffee-script/
4 +
5 +
6 + $ ->
7 + $("#live_submit").on "click", (event) ->
8 + h = $("#editor_text")
9 + e = ace.edit("editor")
10 + h.val(e.getValue())
11 +
12 + $("#language_id").on "change", (event) ->
13 + text = $("#language_id option:selected").text()
14 + mode = 'ace/mode/c_cpp'
15 + switch text
16 + when 'Pascal' then mode = 'ace/mode/pascal'
17 + when 'C++','C' then mode = 'ace/mode/c_cpp'
18 + when 'Ruby' then mode = 'ace/mode/ruby'
19 + when 'Python' then mode = 'ace/mode/python'
20 + when 'Java' then mode = 'ace/mode/java'
21 + editor = ace.edit('editor')
22 + editor.getSession().setMode(mode)
23 +
24 + e = ace.edit("editor")
25 + e.setValue($("#text_haha").val())
26 + e.gotoLine(1)
27 + $("#language_id").trigger('change')
28 +
29 +
30 +
31 +
32 + return
new file 100644
new file 100644
new file 100644
new file 100644
new file 100644
new file 100644
new file 100644
new file 100644
new file 100644
new file 100644
new file 100644
new file 100644
new file 100644
new file 100644
new file 100644
new file 100644
@@ -0,0 +1,4
1 + // Place all the styles related to the sources controller here.
2 + // They will automatically be included in application.css.
3 + // You can use Sass (SCSS) here: http://sass-lang.com/
4 +
new file 100644
new file 100644
new file 100644
new file 100644
@@ -0,0 +1,27
1 + class SourcesController < ApplicationController
2 + before_filter :authenticate
3 +
4 + def direct_edit
5 + @problem = Problem.find(params[:pid])
6 + @source = ''
7 + end
8 +
9 + def direct_edit_submission
10 + @submission = Submission.find(params[:sid])
11 + @source = @submission.source.to_s
12 + @problem = @submission.problem
13 + @lang_id = @submission.language.id
14 + render 'direct_edit'
15 + end
16 +
17 + def get_latest_submission_status
18 + @problem = Problem.find(params[:pid])
19 + @submission = Submission.find_last_by_user_and_problem(params[:uid],params[:pid])
20 + puts User.find(params[:uid]).login
21 + puts Problem.find(params[:pid]).name
22 + puts 'nil' unless @submission
23 + respond_to do |format|
24 + format.js
25 + end
26 + end
27 + end
@@ -0,0 +1,2
1 + module SourcesHelper
2 + end
@@ -0,0 +1,37
1 + %h1 Listing announcements
2 +
3 + = link_to '+ Add announcement', new_announcement_path, class: 'btn btn-success'
4 + %br
5 + %br
6 +
7 + %table.table.table-striped
8 + %thead
9 + %th Updated
10 + %th Announcement
11 + %th Author
12 + %th{style: 'width: 100px'} Published?
13 + %th{style: 'width: 100px'}Front?
14 + %th
15 + %th
16 + - for announcement in @announcements
17 + %tr
18 + - @announcement = announcement
19 + %td= time_ago_in_words announcement.updated_at
20 + %td
21 + - if !announcement.title.blank?
22 + %b Title:
23 + = h announcement.title
24 + %br/
25 + - if !announcement.notes.blank?
26 + %b
27 + Notes: #{h announcement.notes}
28 + %br/
29 + = h announcement.body
30 + %td= h announcement.author
31 + %td= toggle_button(announcement.published?, toggle_announcement_url(@announcement), "announcement_toggle_#{@announcement.id}", {size: 'btn-sm'})
32 + %td= toggle_button(announcement.frontpage?, toggle_front_announcement_url(@announcement), "announcement_toggle_front_#{@announcement.id}", {size: 'btn-sm'})
33 + %td= link_to 'Edit', edit_announcement_path(announcement), class: 'btn btn-block btn-sm btn-info'
34 + %td= link_to 'Destroy', announcement, :confirm => 'Are you sure?', :method => :delete, class: "btn btn-block btn-sm btn-danger"
35 + %br
36 +
37 + = link_to '+ Add announcement', new_announcement_path, class: 'btn btn-success'
@@ -0,0 +1,26
1 +
2 + - if submission.nil?
3 + = "-"
4 + - else
5 + - if submission.graded_at.nil?
6 + =t 'main.submitted_at'
7 + = format_short_time(submission.submitted_at.localtime)
8 + - else
9 + = t 'main.graded_at'
10 + = "#{format_short_time(submission.graded_at.localtime)}, "
11 + - if GraderConfiguration['ui.show_score']
12 + = t 'main.score'
13 + = "#{(submission.points*100/submission.problem.full_score).to_i} "
14 + = " ["
15 + %tt
16 + = submission.grader_comment
17 + = "]"
18 + - if GraderConfiguration.show_grading_result
19 + = " | "
20 + = link_to '[detailed result]', :action => 'result', :id => submission.id
21 + = " | "
22 + = link_to("[#{t 'main.cmp_msg'}]", {:action => 'compiler_msg', :id => submission.id}, {:popup => true})
23 + = " | "
24 + = link_to("[#{t 'main.src_link'}]",{:action => 'source', :id => submission.id})
25 + //= " | "
26 + //= link_to "[#{t 'main.submissions_link'}]", main_submission_path(submission.problem.id)
@@ -0,0 +1,7
1 + :plain
2 + var t = $("#{button_id}");
3 + t.removeClass('btn-default');
4 + t.removeClass('btn-success');
5 + t.removeClass('btn-warning');
6 + t.addClass("btn-#{button_on ? 'success' : 'default'}");
7 + t.text("#{button_on ? 'Yes' : 'No'}");
@@ -0,0 +1,84
1 + %header.navbar.navbar-default.navbar-fixed-top
2 + %nav
3 + .container-fluid
4 + .navbar-header
5 + %a.navbar-brand{href: main_list_path}
6 + %span.glyphicon.glyphicon-home
7 + MAIN
8 + .collapse.navbar-collapse
9 + %ul.nav.navbar-nav
10 + - if (@current_user!=nil) and (GraderConfiguration.show_tasks_to?(@current_user))
11 + //= add_menu("#{I18n.t 'menu.tasks'}", 'tasks', 'list')
12 + %li.dropdown
13 + %a.dropdown-toggle{href: '#', data: {toggle:'dropdown'}, aria: {haspopup:"true", expanded:"false"}, role: "button"}
14 + = "#{I18n.t 'menu.submissions'}"
15 + %span.caret
16 + %ul.dropdown-menu
17 + = add_menu("View", 'main', 'submission')
18 + = add_menu("Self Test", 'test', 'index')
19 + - if GraderConfiguration['right.user_hall_of_fame']
20 + = add_menu("#{I18n.t 'menu.hall_of_fame'}", 'report', 'problem_hof')
21 + / display MODE button (with countdown in contest mode)
22 + - if GraderConfiguration.analysis_mode?
23 + %div.navbar-btn.btn.btn-success#countdown= "ANALYSIS MODE"
24 + - elsif GraderConfiguration.time_limit_mode?
25 + - if @current_user.contest_finished?
26 + %div.navbar-btn.btn.btn-danger#countdown= "Contest is over"
27 + - elsif !@current_user.contest_started?
28 + %div.navbar-btn.btn.btn-primary#countdown= (t 'title_bar.contest_not_started')
29 + - else
30 + %div.navbar-btn.btn.btn-primary#countdown asdf
31 + :javascript
32 + $("#countdown").countdown({until: "+#{@current_user.contest_time_left.to_i}s", layout: 'Time left: {hnn}:{mnn}:{snn}'});
33 + / admin section
34 + - if (@current_user!=nil) and (session[:admin])
35 + %li.dropdown
36 + %a.dropdown-toggle{href: '#', data: {toggle:'dropdown'}, aria: {haspopup:"true", expanded:"false"}, role: "button"}
37 + Manage
38 + %span.caret
39 + %ul.dropdown-menu
40 + = add_menu( 'Announcements', 'announcements', 'index')
41 + = add_menu( 'Problems', 'problems', 'index')
42 + = add_menu( 'Users', 'user_admin', 'index')
43 + = add_menu( 'Graders', 'graders', 'list')
44 + = add_menu( 'Message ', 'messages', 'console')
45 + %li.divider{role: 'separator'}
46 + = add_menu( 'System config', 'configurations', 'index')
47 + %li.divider{role: 'separator'}
48 + = add_menu( 'Sites', 'sites', 'index')
49 + = add_menu( 'Contests', 'contest_management', 'index')
50 + %li.dropdown
51 + %a.dropdown-toggle{href: '#', data: {toggle:'dropdown'}, aria: {haspopup:"true", expanded:"false"}, role: "button"}
52 + Report
53 + %span.caret
54 + %ul.dropdown-menu
55 + = add_menu( 'Results', 'user_admin', 'user_stat')
56 + = add_menu( 'Report', 'report', 'multiple_login')
57 + - if (ungraded = Submission.where('graded_at is null').where('submitted_at < ?', 1.minutes.ago).count) > 0
58 + =link_to "#{ungraded} backlogs!",
59 + grader_list_path,
60 + class: 'navbar-btn btn btn-default btn-warning', data: {toggle: 'tooltip'},title: 'Number of ungraded submission'
61 +
62 + %ul.nav.navbar-nav.navbar-right
63 + = add_menu("#{content_tag(:span,'',class: 'glyphicon glyphicon-question-sign')}".html_safe, 'main', 'help')
64 + = add_menu("#{content_tag(:span,'',class: 'glyphicon glyphicon-comment')}".html_safe, 'messages', 'list', {title: I18n.t('menu.messages'), data: {toggle: 'tooltip'}})
65 + - if GraderConfiguration['system.user_setting_enabled']
66 + = add_menu("#{content_tag(:span,'',class: 'glyphicon glyphicon-cog')}".html_safe, 'users', 'index', {title: I18n.t('menu.settings'), data: {toggle: 'tooltip'}})
67 + = add_menu("#{content_tag(:span,'',class: 'glyphicon glyphicon-log-out')} #{@current_user.full_name}".html_safe, 'main', 'login', {title: I18n.t('menu.log_out'), data: {toggle: 'tooltip'}})
68 +
69 + /
70 + - if (@current_user!=nil) and (session[:admin])
71 + %nav.navbar.navbar-fixed-top.navbar-inverse.secondnavbar
72 + .container-fluid
73 + .collapse.navbar-collapse
74 + %ul.nav.navbar-nav
75 + = add_menu( '[Announcements]', 'announcements', 'index')
76 + = add_menu( '[Msg console]', 'messages', 'console')
77 + = add_menu( '[Problems]', 'problems', 'index')
78 + = add_menu( '[Users]', 'user_admin', 'index')
79 + = add_menu( '[Results]', 'user_admin', 'user_stat')
80 + = add_menu( '[Report]', 'report', 'multiple_login')
81 + = add_menu( '[Graders]', 'graders', 'list')
82 + = add_menu( '[Contests]', 'contest_management', 'index')
83 + = add_menu( '[Sites]', 'sites', 'index')
84 + = add_menu( '[System config]', 'configurations', 'index')
@@ -0,0 +1,15
1 + <!DOCTYPE html>
2 + %html
3 + %head
4 + %title= GraderConfiguration['contest.name']
5 + = stylesheet_link_tag "application", params[:controller], :media => "all"
6 + = javascript_include_tag "application", params[:controller]
7 + = csrf_meta_tags
8 + = content_for :header
9 + = yield :head
10 +
11 + %body
12 + = render 'layouts/header'
13 +
14 + = content_tag(:p,flash[:notice],class: 'alert alert-success') if flash[:notice]!=nil
15 + = yield
@@ -0,0 +1,17
1 + %tr
2 + %td
3 + = "#{problem.name}"
4 + %td
5 + = "#{problem.full_name}"
6 + = link_to_description_if_any "[#{t 'main.problem_desc'}] <span class='glyphicon glyphicon-file'></span>".html_safe, problem
7 + %td
8 + = @prob_submissions[problem.id][:count]
9 + = link_to "[subs]", main_submission_path(problem.id)
10 + %td
11 + = render :partial => 'submission_short',
12 + :locals => {:submission => @prob_submissions[problem.id][:submission], :problem_name => problem.name }
13 + %td
14 + - if @prob_submissions[problem.id][:submission]
15 + = link_to 'Edit', direct_edit_submission_path(@prob_submissions[problem.id][:submission]), class: 'btn btn-success'
16 + - else
17 + = link_to 'New', direct_edit_path(problem.id), class: 'btn btn-success'
@@ -0,0 +1,20
1 + = form_tag({:action => 'submit'}, :multipart => true, class: 'form') do
2 + - if @submission and @submission.errors.any?
3 + #error_explanation
4 + .alert.alert-danger
5 + %h3= "#{pluralize(@submission.errors.count, "error")} prohibited this user from being saved:"
6 + %ul
7 + - @submission.errors.full_messages.each do |msg|
8 + %li= msg
9 + .form-group
10 + = label_tag :submission, 'Problem:'
11 + = select 'submission', 'problem_id', [[(t 'main.specified_in_header'),'-1']] + @problems.collect {|p| ["[#{p.name}] #{p.full_name}", p.id]}, {:selected => '-1'}, { class: 'select2 form-control' }
12 + .form-group
13 + = label_tag :file, 'File:'
14 + .input-group
15 + %span.input-group-btn
16 + %span.btn.btn-default.btn-file
17 + Browse
18 + = file_field_tag 'file'
19 + = text_field_tag '' , nil, {readonly: true, class: 'form-control'}
20 + = submit_tag 'Submit', class: 'btn btn-default'
@@ -0,0 +1,50
1 + - content_for :head do
2 + = stylesheet_link_tag 'problems'
3 + %h1 Listing problems
4 + %p
5 + = link_to 'New problem', new_problem_path, class: 'btn btn-default btn-sm'
6 + = link_to 'Manage problems', { action: 'manage'}, class: 'btn btn-default btn-sm'
7 + = link_to 'Import problems', {:action => 'import'}, class: 'btn btn-default btn-sm'
8 + = link_to 'Turn off all problems', {:action => 'turn_all_off'}, class: 'btn btn-default btn-sm'
9 + = link_to 'Turn on all problems', {:action => 'turn_all_on'}, class: 'btn btn-default btn-sm'
10 + .submitbox
11 + = form_tag :action => 'quick_create' do
12 + %b Quick New:
13 + %label{:for => "problem_name"} Name
14 + = text_field 'problem', 'name'
15 + |
16 + %label{:for => "problem_full_name"} Full name
17 + = text_field 'problem', 'full_name'
18 + = submit_tag "Create"
19 + %table.table.table-condense.table-hover
20 + %thead
21 + %th Name
22 + %th Full name
23 + %th.text-right Full score
24 + %th Date added
25 + %th.text-center
26 + Avail?
27 + %sup{class: 'text-primary',data: {toggle: 'tooltip'}, title: 'Let user submits to this problem?' } [?]
28 + %th.text-center
29 + Test?
30 + %sup{class: 'text-primary',data: {toggle: 'tooltip'}, title: 'Let user uses test interface on this problem?' } [?]
31 + - if GraderConfiguration.multicontests?
32 + %th Contests
33 + - for problem in @problems
34 + %tr{:class => "#{(problem.available) ? "success" : "danger"}", :id => "prob-#{problem.id}", :name => "prob-#{problem.id}"}
35 + - @problem=problem
36 + %td= in_place_editor_field :problem, :name, {}, :rows=>1
37 + %td= in_place_editor_field :problem, :full_name, {}, :rows=>1
38 + %td.text-right= in_place_editor_field :problem, :full_score, {}, :rows=>1
39 + %td= problem.date_added
40 + %td= toggle_button(@problem.available?, toggle_problem_url(@problem), "problem-avail-#{@problem.id}")
41 + %td= toggle_button(@problem.test_allowed?, toggle_test_problem_url(@problem), "problem-test-#{@problem.id}")
42 + - if GraderConfiguration.multicontests?
43 + %td
44 + = problem.contests.collect { |c| c.name }.join(', ')
45 + %td= link_to 'Stat', {:action => 'stat', :id => problem.id}, class: 'btn btn-info btn-xs btn-block'
46 + %td= link_to 'Show', {:action => 'show', :id => problem}, class: 'btn btn-info btn-xs btn-block'
47 + %td= link_to 'Edit', {:action => 'edit', :id => problem}, class: 'btn btn-info btn-xs btn-block'
48 + %td= link_to 'Destroy', { :action => 'destroy', :id => problem }, :confirm => 'Are you sure?', :method => :post, class: 'btn btn-danger btn-xs btn-block'
49 + %br/
50 + = link_to '[New problem]', :action => 'new'
@@ -0,0 +1,8
1 + = render partial: 'toggle_button',
2 + locals: {button_id: "#problem-avail-#{@problem.id}",button_on: @problem.available }
3 + :plain
4 + r = $("#prob-#{@problem.id}");
5 + r.removeClass('success');
6 + r.removeClass('danger');
7 + r.addClass("#{@problem.available? ? 'success' : 'danger'}");
8 +
@@ -0,0 +1,2
1 + = render partial: 'toggle_button',
2 + locals: {button_id: "#problem-test-#{@problem.id}",button_on: @problem.test_allowed?}
@@ -0,0 +1,24
1 + %h1 Editing site
2 + = error_messages_for :site
3 + = form_for(@site) do |f|
4 + %p
5 + %b Name
6 + %br/
7 + = f.text_field :name
8 + %p
9 + %b Password
10 + %br/
11 + = f.text_field :password
12 + %p
13 + %b Started
14 + %br/
15 + = f.check_box :started
16 + %p
17 + %b Start time
18 + %br/
19 + = f.datetime_select :start_time, :include_blank => true
20 + %p
21 + = f.submit "Update"
22 + = link_to 'Show', @site
23 + |
24 + = link_to 'Back', sites_path
@@ -0,0 +1,24
1 + %h1 Listing sites
2 + %table.table.table-striped
3 + %tr
4 + %th Name
5 + %th Password
6 + %th Started
7 + %th Start time
8 + %th
9 + %th
10 + %th
11 + - for site in @sites
12 + - background = "white"
13 + - background = "grey" if (site.started==true) and (site.finished? == true)
14 + - background = "lightgreen" if (site.started==true) and (site.finished? != true)
15 + %tr{:style => "background: #{background};"}
16 + %td= h site.name
17 + %td= h site.password
18 + %td= h site.started
19 + %td= h site.start_time
20 + %td= link_to 'Show', site, class: 'btn btn-default'
21 + %td= link_to 'Edit', edit_site_path(site), class: 'btn btn-default'
22 + %td= link_to 'Destroy', site, :confirm => 'Are you sure?', :method => :delete, class: 'btn btn-default'
23 + %br/
24 + = link_to '+ New site', new_site_path, class: 'btn btn-success'
@@ -0,0 +1,22
1 + %h1 New site
2 + = error_messages_for :site
3 + = form_for(@site) do |f|
4 + %p
5 + %b Name
6 + %br/
7 + = f.text_field :name
8 + %p
9 + %b Password
10 + %br/
11 + = f.text_field :password
12 + %p
13 + %b Started
14 + %br/
15 + = f.check_box :started
16 + %p
17 + %b Start time
18 + %br/
19 + = f.datetime_select :start_time
20 + %p
21 + = f.submit "Create"
22 + = link_to 'Back', sites_path
@@ -0,0 +1,15
1 + %p
2 + %b Name:
3 + = h @site.name
4 + %p
5 + %b Password:
6 + = h @site.password
7 + %p
8 + %b Started:
9 + = h @site.started
10 + %p
11 + %b Start time:
12 + = h @site.start_time
13 + = link_to 'Edit', edit_site_path(@site)
14 + |
15 + = link_to 'Back', sites_path
@@ -0,0 +1,264
1 + %h2 Live submit
2 + %br
3 +
4 + %textarea#text_haha{style: "display:none"}~ @source
5 + .container
6 + .row
7 + .col-md-12
8 + .alert.alert-info
9 + Write your code in the following box, choose language, and click submit button when finished
10 + .row
11 + .col-md-8
12 + %div#editor{style: 'height: 500px; border-radius: 7px; font-size: 14px;'}
13 + .col-md-4
14 + = form_tag({controller: :main, :action => 'submit'}, :multipart => true, class: 'form') do
15 +
16 + = hidden_field_tag 'editor_text', @source
17 + = hidden_field_tag 'submission[problem_id]', @problem.id
18 + .form-group
19 + = label_tag "Task:"
20 + = text_field_tag 'asdf', "#{@problem.long_name}", class: 'form-control', disabled: true
21 +
22 + .form-group
23 + = label_tag 'Language'
24 + = select_tag 'language_id', options_from_collection_for_select(Language.all, 'id', 'pretty_name', @lang_id || Language.find_by_pretty_name("Python").id || Language.first.id), class: 'form-control select', style: "width: 100px"
25 + .form-group
26 + = submit_tag 'Submit', class: 'btn btn-success', id: 'live_submit',
27 + data: {confirm: "Submitting this source code for task #{@problem.long_name}?"}
28 + .panel.panel-info
29 + .panel-heading
30 + Latest Submission Status
31 + .panel-body
32 + - if @submission
33 + = render :partial => 'submission_short',
34 + :locals => {:submission => @submission, :problem_name => @problem.name }
35 + .row
36 + .col-md-12
37 + %h2 Console
38 + %textarea#console{style: 'height: 100%; width: 100%;background-color:#000;color:#fff;font-family: consolas, monaco, "Droid Sans Mono";',rows: 20}
39 +
40 + :javascript
41 + $(document).ready(function() {
42 + brython();
43 + });
44 +
45 +
46 + %script#__main__{type:'text/python3'}
47 + :plain
48 + import sys
49 + import traceback
50 +
51 + from browser import document as doc
52 + from browser import window, alert, console
53 +
54 + _credits = """ Thanks to CWI, CNRI, BeOpen.com, Zope Corporation and a cast of thousands
55 + for supporting Python development. See www.python.org for more information."""
56 +
57 + _copyright = """Copyright (c) 2012, Pierre Quentel pierre.quentel@gmail.com
58 + All Rights Reserved.
59 +
60 + Copyright (c) 2001-2013 Python Software Foundation.
61 + All Rights Reserved.
62 +
63 + Copyright (c) 2000 BeOpen.com.
64 + All Rights Reserved.
65 +
66 + Copyright (c) 1995-2001 Corporation for National Research Initiatives.
67 + All Rights Reserved.
68 +
69 + Copyright (c) 1991-1995 Stichting Mathematisch Centrum, Amsterdam.
70 + All Rights Reserved."""
71 +
72 + _license = """Copyright (c) 2012, Pierre Quentel pierre.quentel@gmail.com
73 + All rights reserved.
74 +
75 + Redistribution and use in source and binary forms, with or without
76 + modification, are permitted provided that the following conditions are met:
77 +
78 + Redistributions of source code must retain the above copyright notice, this
79 + list of conditions and the following disclaimer. Redistributions in binary
80 + form must reproduce the above copyright notice, this list of conditions and
81 + the following disclaimer in the documentation and/or other materials provided
82 + with the distribution.
83 + Neither the name of the <ORGANIZATION> nor the names of its contributors may
84 + be used to endorse or promote products derived from this software without
85 + specific prior written permission.
86 +
87 + THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
88 + AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
89 + IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
90 + ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
91 + LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
92 + CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
93 + SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
94 + INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
95 + CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
96 + ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
97 + POSSIBILITY OF SUCH DAMAGE.
98 + """
99 +
100 + def credits():
101 + print(_credits)
102 + credits.__repr__ = lambda:_credits
103 +
104 + def copyright():
105 + print(_copyright)
106 + copyright.__repr__ = lambda:_copyright
107 +
108 + def license():
109 + print(_license)
110 + license.__repr__ = lambda:_license
111 +
112 + def write(data):
113 + doc['console'].value += str(data)
114 +
115 +
116 + sys.stdout.write = sys.stderr.write = write
117 + history = []
118 + current = 0
119 + _status = "main" # or "block" if typing inside a block
120 +
121 + # execution namespace
122 + editor_ns = {'credits':credits,
123 + 'copyright':copyright,
124 + 'license':license,
125 + '__name__':'__main__'}
126 +
127 + def cursorToEnd(*args):
128 + pos = len(doc['console'].value)
129 + doc['console'].setSelectionRange(pos, pos)
130 + doc['console'].scrollTop = doc['console'].scrollHeight
131 +
132 + def get_col(area):
133 + # returns the column num of cursor
134 + sel = doc['console'].selectionStart
135 + lines = doc['console'].value.split('\n')
136 + for line in lines[:-1]:
137 + sel -= len(line) + 1
138 + return sel
139 +
140 +
141 + def myKeyPress(event):
142 + global _status, current
143 + if event.keyCode == 9: # tab key
144 + event.preventDefault()
145 + doc['console'].value += " "
146 + elif event.keyCode == 13: # return
147 + src = doc['console'].value
148 + if _status == "main":
149 + currentLine = src[src.rfind('>>>') + 4:]
150 + elif _status == "3string":
151 + currentLine = src[src.rfind('>>>') + 4:]
152 + currentLine = currentLine.replace('\n... ', '\n')
153 + else:
154 + currentLine = src[src.rfind('...') + 4:]
155 + if _status == 'main' and not currentLine.strip():
156 + doc['console'].value += '\n>>> '
157 + event.preventDefault()
158 + return
159 + doc['console'].value += '\n'
160 + history.append(currentLine)
161 + current = len(history)
162 + if _status == "main" or _status == "3string":
163 + try:
164 + _ = editor_ns['_'] = eval(currentLine, editor_ns)
165 + if _ is not None:
166 + write(repr(_)+'\n')
167 + doc['console'].value += '>>> '
168 + _status = "main"
169 + except IndentationError:
170 + doc['console'].value += '... '
171 + _status = "block"
172 + except SyntaxError as msg:
173 + if str(msg) == 'invalid syntax : triple string end not found' or \
174 + str(msg).startswith('Unbalanced bracket'):
175 + doc['console'].value += '... '
176 + _status = "3string"
177 + elif str(msg) == 'eval() argument must be an expression':
178 + try:
179 + exec(currentLine, editor_ns)
180 + except:
181 + traceback.print_exc()
182 + doc['console'].value += '>>> '
183 + _status = "main"
184 + elif str(msg) == 'decorator expects function':
185 + doc['console'].value += '... '
186 + _status = "block"
187 + else:
188 + traceback.print_exc()
189 + doc['console'].value += '>>> '
190 + _status = "main"
191 + except:
192 + traceback.print_exc()
193 + doc['console'].value += '>>> '
194 + _status = "main"
195 + elif currentLine == "": # end of block
196 + block = src[src.rfind('>>>') + 4:].splitlines()
197 + block = [block[0]] + [b[4:] for b in block[1:]]
198 + block_src = '\n'.join(block)
199 + # status must be set before executing code in globals()
200 + _status = "main"
201 + try:
202 + _ = exec(block_src, editor_ns)
203 + if _ is not None:
204 + print(repr(_))
205 + except:
206 + traceback.print_exc()
207 + doc['console'].value += '>>> '
208 + else:
209 + doc['console'].value += '... '
210 +
211 + cursorToEnd()
212 + event.preventDefault()
213 +
214 + def myKeyDown(event):
215 + global _status, current
216 + if event.keyCode == 37: # left arrow
217 + sel = get_col(doc['console'])
218 + if sel < 5:
219 + event.preventDefault()
220 + event.stopPropagation()
221 + elif event.keyCode == 36: # line start
222 + pos = doc['console'].selectionStart
223 + col = get_col(doc['console'])
224 + doc['console'].setSelectionRange(pos - col + 4, pos - col + 4)
225 + event.preventDefault()
226 + elif event.keyCode == 38: # up
227 + if current > 0:
228 + pos = doc['console'].selectionStart
229 + col = get_col(doc['console'])
230 + # remove current line
231 + doc['console'].value = doc['console'].value[:pos - col + 4]
232 + current -= 1
233 + doc['console'].value += history[current]
234 + event.preventDefault()
235 + elif event.keyCode == 40: # down
236 + if current < len(history) - 1:
237 + pos = doc['console'].selectionStart
238 + col = get_col(doc['console'])
239 + # remove current line
240 + doc['console'].value = doc['console'].value[:pos - col + 4]
241 + current += 1
242 + doc['console'].value += history[current]
243 + event.preventDefault()
244 + elif event.keyCode == 8: # backspace
245 + src = doc['console'].value
246 + lstart = src.rfind('\n')
247 + if (lstart == -1 and len(src) < 5) or (len(src) - lstart < 6):
248 + event.preventDefault()
249 + event.stopPropagation()
250 +
251 +
252 + doc['console'].bind('keypress', myKeyPress)
253 + doc['console'].bind('keydown', myKeyDown)
254 + doc['console'].bind('click', cursorToEnd)
255 + v = sys.implementation.version
256 + doc['console'].value = "Brython %s.%s.%s on %s %s\n>>> " % (
257 + v[0], v[1], v[2], window.navigator.appName, window.navigator.appVersion)
258 + #doc['console'].value += 'Type "copyright", "credits" or "license" for more information.'
259 + doc['console'].focus()
260 + cursorToEnd()
261 +
262 +
263 +
264 +
@@ -0,0 +1,2
1 + :javascript
2 + $("#latest_status").html("#{j render({partial: 'submission_short', locals: {submission: @submission, problem_name: @problem.name}})}")
@@ -0,0 +1,100
1 + %h1 Listing users
2 +
3 + .panel.panel-primary
4 + .panel-title.panel-heading
5 + Quick Add
6 + .panel-body
7 + = form_tag( {method: 'post'}, {class: 'form-inline'}) do
8 + .form-group
9 + = label_tag 'user_login', 'Login'
10 + = text_field 'user', 'login', :size => 10,class: 'form-control'
11 + .form-group
12 + = label_tag 'user_full_name', 'Full Name'
13 + = text_field 'user', 'full_name', :size => 10,class: 'form-control'
14 + .form-group
15 + = label_tag 'user_password', 'Password'
16 + = text_field 'user', 'password', :size => 10,class: 'form-control'
17 + .form-group
18 + = label_tag 'user_password_confirmation', 'Confirm'
19 + = text_field 'user', 'password_confirmation', :size => 10,class: 'form-control'
20 + .form-group
21 + = label_tag 'user_email', 'email'
22 + = text_field 'user', 'email', :size => 10,class: 'form-control'
23 + =submit_tag "Create", class: 'btn btn-primary'
24 +
25 + .panel.panel-primary
26 + .panel-title.panel-heading
27 + Import from site management
28 + .panel-body
29 + = form_tag({:action => 'import'}, :multipart => true,class: 'form form-inline') do
30 + .form-group
31 + = label_tag :file, 'File:'
32 + .input-group
33 + %span.input-group-btn
34 + %span.btn.btn-default.btn-file
35 + Browse
36 + = file_field_tag 'file'
37 + = text_field_tag '' , nil, {readonly: true, class: 'form-control'}
38 + = submit_tag 'Submit', class: 'btn btn-default'
39 +
40 +
41 + %p
42 + = link_to '+ New user', { :action => 'new' }, { class: 'btn btn-success '}
43 + = link_to '+ New list of users', { :action => 'new_list' }, { class: 'btn btn-success '}
44 + = link_to 'View administrators',{ :action => 'admin'}, { class: 'btn btn-default '}
45 + = link_to 'Random passwords',{ :action => 'random_all_passwords'}, { class: 'btn btn-default '}
46 + = link_to 'View active users',{ :action => 'active'}, { class: 'btn btn-default '}
47 + = link_to 'Mass mailing',{ :action => 'mass_mailing'}, { class: 'btn btn-default '}
48 +
49 + - if GraderConfiguration.multicontests?
50 + %br/
51 + %b Multi-contest:
52 + = link_to '[Manage bulk users in contests]', :action => 'contest_management'
53 + View users in:
54 + - @contests.each do |contest|
55 + = link_to "[#{contest.name}]", :action => 'contests', :id => contest.id
56 + = link_to "[no contest]", :action => 'contests', :id => 'none'
57 +
58 + Total #{@user_count} users |
59 + - if !@paginated
60 + Display all users.
61 + \#{link_to '[show in pages]', :action => 'index', :page => '1'}
62 + - else
63 + Display in pages.
64 + \#{link_to '[display all]', :action => 'index', :page => 'all'} |
65 + \#{will_paginate @users, :container => false}
66 +
67 +
68 + %table.table.table-hover.table-condense
69 + %thead
70 + %th Login
71 + %th Full name
72 + %th email
73 + %th Remark
74 + %th
75 + Activated
76 + %sup{class: 'text-primary',data: {toggle: 'tooltip', placement: 'top'}, title: 'User has already confirmed the email?' } [?]
77 + %th
78 + Enabled
79 + %sup{class: 'text-primary',data: {toggle: 'tooltip', placement: 'top'}, title: 'Allow the user to login?' } [?]
80 + %th Last IP
81 + %th
82 + %th
83 + %th
84 + %th
85 + - for user in @users
86 + %tr
87 + %td= link_to user.login, controller: :users, :action => 'profile', :id => user
88 + %td= user.full_name
89 + %td= user.email
90 + %td= user.remark
91 + %td= toggle_button(user.activated?, toggle_activate_user_url(user),"toggle_activate_user_#{user.id}")
92 + %td= toggle_button(user.enabled?, toggle_enable_user_url(user),"toggle_enable_user_#{user.id}")
93 + %td= user.last_ip
94 + %td= link_to 'Clear IP', {:action => 'clear_last_ip', :id => user, :page=>params[:page]}, :confirm => 'This will reset last logging in ip of the user, are you sure?', class: 'btn btn-default btn-xs btn-block'
95 + %td= link_to 'Show', {:action => 'show', :id => user}, class: 'btn btn-default btn-xs btn-block'
96 + %td= link_to 'Edit', {:action => 'edit', :id => user}, class: 'btn btn-default btn-xs btn-block'
97 + %td= link_to 'Destroy', { :action => 'destroy', :id => user }, :confirm => 'Are you sure?', :method => :post, class: 'btn btn-danger btn-xs btn-block'
98 + %br/
99 + = link_to '+ New user', { :action => 'new' }, { class: 'btn btn-success '}
100 + = link_to '+ New list of users', { :action => 'new_list' }, { class: 'btn btn-success '}
@@ -0,0 +1,3
1 + class ActiveRecord::ConnectionAdapters::Mysql2Adapter
2 + NATIVE_DATABASE_TYPES[:primary_key] = "int(11) auto_increment PRIMARY KEY"
3 + end
@@ -0,0 +1,12
1 + require 'spec_helper'
2 +
3 + describe SourcesController do
4 +
5 + describe "GET 'direct_edit'" do
6 + it "returns http success" do
7 + get 'direct_edit'
8 + response.should be_success
9 + end
10 + end
11 +
12 + end
@@ -0,0 +1,15
1 + require 'spec_helper'
2 +
3 + # Specs in this file have access to a helper object that includes
4 + # the SourcesHelper. For example:
5 + #
6 + # describe SourcesHelper do
7 + # describe "string concat" do
8 + # it "concats two strings with spaces" do
9 + # expect(helper.concat_strings("this","that")).to eq("this that")
10 + # end
11 + # end
12 + # end
13 + describe SourcesHelper do
14 + pending "add some examples to (or delete) #{__FILE__}"
15 + end
@@ -0,0 +1,5
1 + require 'spec_helper'
2 +
3 + describe "sources/direct_edit.html.haml" do
4 + pending "add some examples to (or delete) #{__FILE__}"
5 + end
@@ -2,6 +2,8
2
2
3 gem 'rails', '3.2.21'
3 gem 'rails', '3.2.21'
4
4
5 + gem 'select2-rails'
6 +
5 # Bundle edge Rails instead:
7 # Bundle edge Rails instead:
6 # gem 'rails', :git => 'git://github.com/rails/rails.git'
8 # gem 'rails', :git => 'git://github.com/rails/rails.git'
7
9
@@ -45,11 +47,26
45 gem 'jquery-ui-sass-rails'
47 gem 'jquery-ui-sass-rails'
46 gem 'jquery-timepicker-addon-rails'
48 gem 'jquery-timepicker-addon-rails'
47 gem 'jquery-tablesorter'
49 gem 'jquery-tablesorter'
50 + gem 'jquery-countdown-rails'
48
51
49 #syntax highlighter
52 #syntax highlighter
50 gem 'rouge'
53 gem 'rouge'
51
54
55 + #add bootstrap
56 + gem 'bootstrap-sass', '~> 3.2.0'
57 + gem 'bootstrap-switch-rails'
58 + gem 'bootstrap-toggle-rails'
59 + gem 'autoprefixer-rails'
60 +
61 + #bootstrap sortable
62 + gem 'momentjs-rails'
63 + gem 'rails_bootstrap_sortable'
64 +
65 + #ace editor
66 + gem 'ace-rails-ap'
67 +
52 gem 'haml'
68 gem 'haml'
69 + gem 'haml-rails'
53 gem 'mail'
70 gem 'mail'
54 gem 'rdiscount'
71 gem 'rdiscount'
55 gem 'test-unit'
72 gem 'test-unit'
@@ -9,6 +9,7
9 GEM
9 GEM
10 remote: https://rubygems.org/
10 remote: https://rubygems.org/
11 specs:
11 specs:
12 + ace-rails-ap (4.0.2)
12 actionmailer (3.2.21)
13 actionmailer (3.2.21)
13 actionpack (= 3.2.21)
14 actionpack (= 3.2.21)
14 mail (~> 2.5.4)
15 mail (~> 2.5.4)
@@ -37,9 +38,16
37 i18n (~> 0.6, >= 0.6.4)
38 i18n (~> 0.6, >= 0.6.4)
38 multi_json (~> 1.0)
39 multi_json (~> 1.0)
39 arel (3.0.3)
40 arel (3.0.3)
41 + autoprefixer-rails (6.0.3)
42 + execjs
43 + json
40 best_in_place (3.0.3)
44 best_in_place (3.0.3)
41 actionpack (>= 3.2)
45 actionpack (>= 3.2)
42 railties (>= 3.2)
46 railties (>= 3.2)
47 + bootstrap-sass (3.2.0.2)
48 + sass (~> 3.2)
49 + bootstrap-switch-rails (3.3.3)
50 + bootstrap-toggle-rails (2.2.1.0)
43 builder (3.0.4)
51 builder (3.0.4)
44 coffee-rails (3.2.2)
52 coffee-rails (3.2.2)
45 coffee-script (>= 2.2.0)
53 coffee-script (>= 2.2.0)
@@ -54,10 +62,16
54 execjs (2.3.0)
62 execjs (2.3.0)
55 haml (4.0.6)
63 haml (4.0.6)
56 tilt
64 tilt
65 + haml-rails (0.4)
66 + actionpack (>= 3.1, < 4.1)
67 + activesupport (>= 3.1, < 4.1)
68 + haml (>= 3.1, < 4.1)
69 + railties (>= 3.1, < 4.1)
57 hike (1.2.3)
70 hike (1.2.3)
58 i18n (0.7.0)
71 i18n (0.7.0)
59 in_place_editing (1.2.0)
72 in_place_editing (1.2.0)
60 journey (1.0.4)
73 journey (1.0.4)
74 + jquery-countdown-rails (2.0.2)
61 jquery-rails (3.1.2)
75 jquery-rails (3.1.2)
62 railties (>= 3.0, < 5.0)
76 railties (>= 3.0, < 5.0)
63 thor (>= 0.14, < 2.0)
77 thor (>= 0.14, < 2.0)
@@ -77,6 +91,8
77 mime-types (~> 1.16)
91 mime-types (~> 1.16)
78 treetop (~> 1.4.8)
92 treetop (~> 1.4.8)
79 mime-types (1.25.1)
93 mime-types (1.25.1)
94 + momentjs-rails (2.11.1)
95 + railties (>= 3.1)
80 multi_json (1.10.1)
96 multi_json (1.10.1)
81 mysql2 (0.3.20)
97 mysql2 (0.3.20)
82 polyglot (0.3.5)
98 polyglot (0.3.5)
@@ -98,6 +114,8
98 activesupport (= 3.2.21)
114 activesupport (= 3.2.21)
99 bundler (~> 1.0)
115 bundler (~> 1.0)
100 railties (= 3.2.21)
116 railties (= 3.2.21)
117 + rails_bootstrap_sortable (2.0.0)
118 + momentjs-rails (~> 2, >= 2.8.3)
101 railties (3.2.21)
119 railties (3.2.21)
102 actionpack (= 3.2.21)
120 actionpack (= 3.2.21)
103 activesupport (= 3.2.21)
121 activesupport (= 3.2.21)
@@ -130,6 +148,8
130 railties (~> 3.2.0)
148 railties (~> 3.2.0)
131 sass (>= 3.1.10)
149 sass (>= 3.1.10)
132 tilt (~> 1.3)
150 tilt (~> 1.3)
151 + select2-rails (4.0.1)
152 + thor (~> 0.14)
133 sprockets (2.2.3)
153 sprockets (2.2.3)
134 hike (~> 1.2)
154 hike (~> 1.2)
135 multi_json (~> 1.0)
155 multi_json (~> 1.0)
@@ -152,23 +172,33
152 ruby
172 ruby
153
173
154 DEPENDENCIES
174 DEPENDENCIES
175 + ace-rails-ap
176 + autoprefixer-rails
155 best_in_place (~> 3.0.1)
177 best_in_place (~> 3.0.1)
178 + bootstrap-sass (~> 3.2.0)
179 + bootstrap-switch-rails
180 + bootstrap-toggle-rails
156 coffee-rails (~> 3.2.2)
181 coffee-rails (~> 3.2.2)
157 dynamic_form
182 dynamic_form
158 haml
183 haml
184 + haml-rails
159 in_place_editing
185 in_place_editing
186 + jquery-countdown-rails
160 jquery-rails
187 jquery-rails
161 jquery-tablesorter
188 jquery-tablesorter
162 jquery-timepicker-addon-rails
189 jquery-timepicker-addon-rails
163 jquery-ui-sass-rails
190 jquery-ui-sass-rails
164 mail
191 mail
192 + momentjs-rails
165 mysql2
193 mysql2
166 prototype-rails
194 prototype-rails
167 rails (= 3.2.21)
195 rails (= 3.2.21)
196 + rails_bootstrap_sortable
168 rdiscount
197 rdiscount
169 rouge
198 rouge
170 rspec-rails (~> 2.99.0)
199 rspec-rails (~> 2.99.0)
171 sass-rails (~> 3.2.6)
200 sass-rails (~> 3.2.6)
201 + select2-rails
172 test-unit
202 test-unit
173 uglifier
203 uglifier
174 verification!
204 verification!
@@ -10,8 +10,35
10 // WARNING: THE FIRST BLANK LINE MARKS THE END OF WHAT'S TO BE PROCESSED, ANY BLANK LINE SHOULD
10 // WARNING: THE FIRST BLANK LINE MARKS THE END OF WHAT'S TO BE PROCESSED, ANY BLANK LINE SHOULD
11 // GO AFTER THE REQUIRES BELOW.
11 // GO AFTER THE REQUIRES BELOW.
12 //
12 //
13 - //= require prototype
13 + //= require jquery
14 - //= require prototype_ujs
14 + //= require jquery_ujs
15 - //= require effects
15 + //= require jquery.ui.all
16 - //= require dragdrop
16 + //= require bootstrap-sprockets
17 - //= require controls
17 + //= require moment
18 + //= require bootstrap-sortable
19 + //= require select2
20 + //= require ace-rails-ap
21 + //= require ace/mode-c_cpp
22 + //= require ace/mode-python
23 + //= require ace/mode-ruby
24 + //= require ace/mode-pascal
25 + //= require ace/mode-javascript
26 + //= require ace/mode-java
27 + //= require ace/theme-merbivore
28 + //= require custom
29 + //= require jquery.countdown
30 + //-------------- addition from local_jquery -----------
31 + //= require jquery.ui.datepicker
32 + //= require jquery.ui.slider
33 + //= require jquery-ui-timepicker-addon
34 + //= require jquery-tablesorter
35 + //= require best_in_place
36 + //= require best_in_place.jquery-ui
37 + //= require brython
38 +
39 + // since this is after blank line, it is not downloaded
40 + //x= require prototype
41 + //x= require prototype_ujs
42 + //x= require effects
43 + //x= require dragdrop
44 + //x= require controls
@@ -1,3 +0,0
1 - # Place all the behaviors and hooks related to the matching controller here.
2 - # All this logic will automatically be available in application.js.
3 - # You can use CoffeeScript in this file: http://jashkenas.github.com/coffee-script/
@@ -1,19 +1,150
1 + /*
2 + * This is a manifest file that'll be compiled into application.css, which will include all the files
3 + * listed below.
4 + *
5 + * Any CSS and SCSS file within this directory, lib/assets/stylesheets, vendor/assets/stylesheets,
6 + * or any plugin's vendor/assets/stylesheets directory can be referenced here using a relative path.
7 + *
8 + * You're free to add application-wide styles to this file and they'll appear at the bottom of the
9 + * compiled file so the styles you add here take precedence over styles defined in any styles
10 + * defined in the other CSS/SCSS files in this directory. It is generally better to create a new
11 + * file per style scope.
12 + *
13 + // bootstrap says that we should not do this, but @import each file instead
14 + # *= require_tree .
15 + # *= require_self
16 + */
1
17
18 + @import jquery.ui.all
2 @import jquery.ui.core
19 @import jquery.ui.core
3 @import jquery.ui.theme
20 @import jquery.ui.theme
4 @import jquery.ui.datepicker
21 @import jquery.ui.datepicker
5 @import jquery.ui.slider
22 @import jquery.ui.slider
6 @import jquery-ui-timepicker-addon
23 @import jquery-ui-timepicker-addon
7 @import jquery-tablesorter/theme.metro-dark
24 @import jquery-tablesorter/theme.metro-dark
25 + @import jquery.countdown
8 @import tablesorter-theme.cafe
26 @import tablesorter-theme.cafe
9
27
28 + //bootstrap
29 + @import bootstrap-sprockets
30 + @import bootstrap
31 + @import select2
32 + @import select2-bootstrap
33 + //@import bootstrap3-switch
34 + @import bootstrap-toggle
35 + @import bootstrap-sortable
36 +
37 + //bootstrap navbar color (from)
38 + $bgDefault : #19197b
39 + $bgHighlight : #06064b
40 + $colDefault : #8e8eb4
41 + $colHighlight : #ffffff
42 + $dropDown : false
43 + .navbar-default
44 + background-color: $bgDefault
45 + border-color: $bgHighlight
46 + .navbar-brand
47 + color: $colDefault
48 + &:hover, &:focus
49 + color: $colHighlight
50 + .navbar-text
51 + color: $colDefault
52 + .navbar-nav
53 + > li
54 + > a
55 + color: $colDefault
56 + &:hover, &:focus
57 + color: $colHighlight
58 + @if $dropDown
59 + > .dropdown-menu
60 + background-color: $bgDefault
61 + > li
62 + > a
63 + color: $colDefault
64 + &:hover, &:focus
65 + color: $colHighlight
66 + background-color: $bgHighlight
67 + > .divider
68 + background-color: $bgHighlight
69 + @if $dropDown
70 + .open .dropdown-menu > .active
71 + > a, > a:hover, > a:focus
72 + color: $colHighlight
73 + background-color: $bgHighlight
74 + > .active
75 + > a, > a:hover, > a:focus
76 + color: $colHighlight
77 + background-color: $bgHighlight
78 + > .open
79 + > a, > a:hover, > a:focus
80 + color: $colHighlight
81 + background-color: $bgHighlight
82 + .navbar-toggle
83 + border-color: $bgHighlight
84 + &:hover, &:focus
85 + background-color: $bgHighlight
86 + .icon-bar
87 + background-color: $colDefault
88 + .navbar-collapse,
89 + .navbar-form
90 + border-color: $colDefault
91 + .navbar-link
92 + color: $colDefault
93 + &:hover
94 + color: $colHighlight
95 + @media (max-width: 767px)
96 + .navbar-default .navbar-nav .open .dropdown-menu
97 + > li > a
98 + color: $colDefault
99 + &:hover, &:focus
100 + color: $colHighlight
101 + > .active
102 + > a, > a:hover, > a:focus
103 + color: $colHighlight
104 + background-color: $bgHighlight
105 +
106 + .secondnavbar
107 + top: 50px
108 +
109 +
110 + // --------------- bootstrap file upload ----------------------
111 + .btn-file
112 + position: relative
113 + overflow: hidden
114 +
115 + .btn-file input[type=file]
116 + position: absolute
117 + top: 0
118 + right: 0
119 + min-width: 100%
120 + min-height: 100%
121 + font-size: 100px
122 + text-align: right
123 + filter: alpha(opacity=0)
124 + opacity: 0
125 + outline: none
126 + background: white
127 + cursor: inherit
128 + display: block
129 +
10 body
130 body
11 background: white image-url("topbg.jpg") repeat-x top center
131 background: white image-url("topbg.jpg") repeat-x top center
12 - font-size: 13px
132 + //font-size: 13px
13 - font-family: Tahoma, "sans-serif"
133 + //font-family: Tahoma, "sans-serif"
14 margin: 10px
134 margin: 10px
15 padding: 10px
135 padding: 10px
136 + padding-top: 60px
16
137
138 + // ------------------ bootstrap sortable --------------------
139 + table.sortable th
140 + padding-right: 20px !important
141 + span.sign
142 + right: -15px !important
143 + &.text-right
144 + padding-left: 20px !important
145 + padding-right: 8px !important
146 + &:after, span.sign
147 + left: -15px !important
17
148
18 input
149 input
19 font-family: Tahoma, "sans-serif"
150 font-family: Tahoma, "sans-serif"
@@ -36,17 +167,17
36 border-bottom: 1px solid #eeeeee
167 border-bottom: 1px solid #eeeeee
37
168
38
169
39 - a
170 + //#a
40 - color: #6666cc
171 + // color: #6666cc
41 - text-decoration: none
172 + // text-decoration: none
42 -
173 + //
43 - &:link, &:visited
174 + // &:link, &:visited
44 - color: #6666cc
175 + // color: #6666cc
45 - text-decoration: none
176 + // text-decoration: none
46 -
177 + //
47 - &:hover, &:focus
178 + // &:hover, &:focus
48 - color: #111166
179 + // color: #111166
49 - text-decoration: none
180 + // text-decoration: none
50
181
51
182
52 div
183 div
@@ -3,7 +3,7
3 *************/
3 *************/
4 /* overall */
4 /* overall */
5 .tablesorter-cafe {
5 .tablesorter-cafe {
6 - // font: 12px/18px 'Segoe UI Semilight', 'Open Sans', Verdana, Arial, Helvetica, sans-serif;
6 + /* font: 12px/18px 'Segoe UI Semilight', 'Open Sans', Verdana, Arial, Helvetica, sans-serif; */
7 color: #000;
7 color: #000;
8 background-color: #777;
8 background-color: #777;
9 margin: 10px 0 15px;
9 margin: 10px 0 15px;
@@ -25,8 +25,10
25 .tablesorter-cafe thead td,
25 .tablesorter-cafe thead td,
26 .tablesorter-cafe tfoot th,
26 .tablesorter-cafe tfoot th,
27 .tablesorter-cafe tfoot td {
27 .tablesorter-cafe tfoot td {
28 + /*
28 //font-weight: 300;
29 //font-weight: 300;
29 //font-size: 15px;
30 //font-size: 15px;
31 + */
30 color: #fff;
32 color: #fff;
31 background-color: #777;
33 background-color: #777;
32 padding: 2px;
34 padding: 2px;
@@ -69,14 +69,34
69 if @announcement.update_attributes(params[:announcement])
69 if @announcement.update_attributes(params[:announcement])
70 flash[:notice] = 'Announcement was successfully updated.'
70 flash[:notice] = 'Announcement was successfully updated.'
71 format.html { redirect_to(@announcement) }
71 format.html { redirect_to(@announcement) }
72 + format.js {}
72 format.xml { head :ok }
73 format.xml { head :ok }
73 else
74 else
74 format.html { render :action => "edit" }
75 format.html { render :action => "edit" }
76 + format.js {}
75 format.xml { render :xml => @announcement.errors, :status => :unprocessable_entity }
77 format.xml { render :xml => @announcement.errors, :status => :unprocessable_entity }
76 end
78 end
77 end
79 end
78 end
80 end
79
81
82 + def toggle
83 + @announcement = Announcement.find(params[:id])
84 + @announcement.update_attributes( published: !@announcement.published? )
85 + respond_to do |format|
86 + format.js { render partial: 'toggle_button',
87 + locals: {button_id: "#announcement_toggle_#{@announcement.id}",button_on: @announcement.published? } }
88 + end
89 + end
90 +
91 + def toggle_front
92 + @announcement = Announcement.find(params[:id])
93 + @announcement.update_attributes( frontpage: !@announcement.frontpage? )
94 + respond_to do |format|
95 + format.js { render partial: 'toggle_button',
96 + locals: {button_id: "#announcement_toggle_front_#{@announcement.id}",button_on: @announcement.frontpage? } }
97 + end
98 + end
99 +
80 # DELETE /announcements/1
100 # DELETE /announcements/1
81 # DELETE /announcements/1.xml
101 # DELETE /announcements/1.xml
82 def destroy
102 def destroy
@@ -1,9 +1,17
1 class ApplicationController < ActionController::Base
1 class ApplicationController < ActionController::Base
2 protect_from_forgery
2 protect_from_forgery
3
3
4 + before_filter :current_user
5 +
4 SINGLE_USER_MODE_CONF_KEY = 'system.single_user_mode'
6 SINGLE_USER_MODE_CONF_KEY = 'system.single_user_mode'
5 MULTIPLE_IP_LOGIN_CONF_KEY = 'right.multiple_ip_login'
7 MULTIPLE_IP_LOGIN_CONF_KEY = 'right.multiple_ip_login'
6
8
9 + # Returns the current logged-in user (if any).
10 + def current_user
11 + return nil unless session[:user_id]
12 + @current_user ||= User.find(session[:user_id])
13 + end
14 +
7 def admin_authorization
15 def admin_authorization
8 return false unless authenticate
16 return false unless authenticate
9 user = User.find(session[:user_id], :include => ['roles'])
17 user = User.find(session[:user_id], :include => ['roles'])
@@ -39,12 +47,17
39
47
40 # check if run in single user mode
48 # check if run in single user mode
41 if GraderConfiguration[SINGLE_USER_MODE_CONF_KEY]
49 if GraderConfiguration[SINGLE_USER_MODE_CONF_KEY]
42 - user = User.find(session[:user_id])
50 + user = User.find_by_id(session[:user_id])
43 if user==nil or (not user.admin?)
51 if user==nil or (not user.admin?)
44 flash[:notice] = 'You cannot log in at this time'
52 flash[:notice] = 'You cannot log in at this time'
45 redirect_to :controller => 'main', :action => 'login'
53 redirect_to :controller => 'main', :action => 'login'
46 return false
54 return false
47 end
55 end
56 + unless user.enabled?
57 + flash[:notice] = 'Your account is disabled'
58 + redirect_to :controller => 'main', :action => 'login'
59 + return false
60 + end
48 return true
61 return true
49 end
62 end
50
63
@@ -69,6 +69,14
69 @submission.source.encode!('UTF-8','UTF-8',invalid: :replace, replace: '')
69 @submission.source.encode!('UTF-8','UTF-8',invalid: :replace, replace: '')
70 @submission.source_filename = params['file'].original_filename
70 @submission.source_filename = params['file'].original_filename
71 end
71 end
72 +
73 + if (params[:editor_text])
74 + language = Language.find_by_id(params[:language_id])
75 + @submission.source = params[:editor_text]
76 + @submission.source_filename = "live_edit.#{language.ext}"
77 + @submission.language = language
78 + end
79 +
72 @submission.submitted_at = Time.new.gmtime
80 @submission.submitted_at = Time.new.gmtime
73 @submission.ip_address = request.remote_ip
81 @submission.ip_address = request.remote_ip
74
82
@@ -123,8 +131,8
123 @problem = nil
131 @problem = nil
124 @submissions = nil
132 @submissions = nil
125 else
133 else
126 - @problem = Problem.find_by_name(params[:id])
134 + @problem = Problem.find_by_id(params[:id])
127 - if not @problem.available
135 + if (@problem == nil) or (not @problem.available)
128 redirect_to :action => 'list'
136 redirect_to :action => 'list'
129 flash[:notice] = 'Error: submissions for that problem are not viewable.'
137 flash[:notice] = 'Error: submissions for that problem are not viewable.'
130 return
138 return
@@ -7,8 +7,7
7 in_place_edit_for :problem, :full_score
7 in_place_edit_for :problem, :full_score
8
8
9 def index
9 def index
10 - list
10 + @problems = Problem.find(:all, :order => 'date_added DESC')
11 - render :action => 'list'
12 end
11 end
13
12
14 # GETs should be safe (see http://www.w3.org/2001/tag/doc/whenToUseGet.html)
13 # GETs should be safe (see http://www.w3.org/2001/tag/doc/whenToUseGet.html)
@@ -17,11 +16,7
17 :do_manage,
16 :do_manage,
18 :do_import,
17 :do_import,
19 :update ],
18 :update ],
20 - :redirect_to => { :action => :list }
19 + :redirect_to => { :action => :index }
21 -
22 - def list
23 - @problems = Problem.find(:all, :order => 'date_added DESC')
24 - end
25
20
26 def show
21 def show
27 @problem = Problem.find(params[:id])
22 @problem = Problem.find(params[:id])
@@ -45,7 +40,7
45 @problem.description = @description
40 @problem.description = @description
46 if @problem.save
41 if @problem.save
47 flash[:notice] = 'Problem was successfully created.'
42 flash[:notice] = 'Problem was successfully created.'
48 - redirect_to :action => 'list'
43 + redirect_to action: :index
49 else
44 else
50 render :action => 'new'
45 render :action => 'new'
51 end
46 end
@@ -61,10 +56,10
61 @problem.date_added = Time.new
56 @problem.date_added = Time.new
62 if @problem.save
57 if @problem.save
63 flash[:notice] = 'Problem was successfully created.'
58 flash[:notice] = 'Problem was successfully created.'
64 - redirect_to :action => 'list'
59 + redirect_to action: :index
65 else
60 else
66 flash[:notice] = 'Error saving problem'
61 flash[:notice] = 'Error saving problem'
67 - redirect_to :action => 'list'
62 + redirect_to action: :index
68 end
63 end
69 end
64 end
70
65
@@ -121,13 +116,23
121
116
122 def destroy
117 def destroy
123 Problem.find(params[:id]).destroy
118 Problem.find(params[:id]).destroy
124 - redirect_to :action => 'list'
119 + redirect_to action: :index
125 end
120 end
126
121
127 def toggle
122 def toggle
128 @problem = Problem.find(params[:id])
123 @problem = Problem.find(params[:id])
129 - @problem.available = !(@problem.available)
124 + @problem.update_attributes(available: !(@problem.available) )
130 - @problem.save
125 + respond_to do |format|
126 + format.js { }
127 + end
128 + end
129 +
130 + def toggle_test
131 + @problem = Problem.find(params[:id])
132 + @problem.update_attributes(test_allowed: !(@problem.test_allowed?) )
133 + respond_to do |format|
134 + format.js { }
135 + end
131 end
136 end
132
137
133 def turn_all_off
138 def turn_all_off
@@ -136,7 +141,7
136 problem.available = false
141 problem.available = false
137 problem.save
142 problem.save
138 end
143 end
139 - redirect_to :action => 'list'
144 + redirect_to action: :index
140 end
145 end
141
146
142 def turn_all_on
147 def turn_all_on
@@ -145,7 +150,7
145 problem.available = true
150 problem.available = true
146 problem.save
151 problem.save
147 end
152 end
148 - redirect_to :action => 'list'
153 + redirect_to action: :index
149 end
154 end
150
155
151 def stat
156 def stat
@@ -12,6 +12,36
12 admin_authorization
12 admin_authorization
13 }
13 }
14
14
15 + def score
16 + if params[:commit] == 'download csv'
17 + @problems = Problem.all
18 + else
19 + @problems = Problem.find_available_problems
20 + end
21 + @users = User.includes(:contests, :contest_stat).where(enabled: true) #find(:all, :include => [:contests, :contest_stat]).where(enabled: true)
22 + @scorearray = Array.new
23 + @users.each do |u|
24 + ustat = Array.new
25 + ustat[0] = u
26 + @problems.each do |p|
27 + sub = Submission.find_last_by_user_and_problem(u.id,p.id)
28 + if (sub!=nil) and (sub.points!=nil) and p and p.full_score
29 + ustat << [(sub.points.to_f*100/p.full_score).round, (sub.points>=p.full_score)]
30 + else
31 + ustat << [0,false]
32 + end
33 + end
34 + @scorearray << ustat
35 + end
36 + if params[:commit] == 'download csv' then
37 + csv = gen_csv_from_scorearray(@scorearray,@problems)
38 + send_data csv, filename: 'last_score.csv'
39 + else
40 + render template: 'user_admin/user_stat'
41 + end
42 +
43 + end
44 +
15 def login_stat
45 def login_stat
16 @logins = Array.new
46 @logins = Array.new
17
47
@@ -73,12 +103,7
73 Submission.where("submitted_at >= ? AND submitted_at <= ?",@since_time,@until_time).find_each do |s|
103 Submission.where("submitted_at >= ? AND submitted_at <= ?",@since_time,@until_time).find_each do |s|
74 if @submissions[s.user_id]
104 if @submissions[s.user_id]
75 if not @submissions[s.user_id][:sub].has_key?(s.problem_id)
105 if not @submissions[s.user_id][:sub].has_key?(s.problem_id)
76 - a = nil
106 + a = Problem.find_by_id(s.problem_id)
77 - begin
78 - a = Problem.find(s.problem_id)
79 - rescue
80 - a = nil
81 - end
82 @submissions[s.user_id][:sub][s.problem_id] =
107 @submissions[s.user_id][:sub][s.problem_id] =
83 { prob_name: (a ? a.full_name : '(NULL)'),
108 { prob_name: (a ? a.full_name : '(NULL)'),
84 sub_ids: [s.id] }
109 sub_ids: [s.id] }
@@ -17,7 +17,6
17
17
18 def index
18 def index
19 list
19 list
20 - render :action => 'list'
21 end
20 end
22
21
23 def list
22 def list
@@ -56,7 +55,7
56 @user.activated = true
55 @user.activated = true
57 if @user.save
56 if @user.save
58 flash[:notice] = 'User was successfully created.'
57 flash[:notice] = 'User was successfully created.'
59 - redirect_to :action => 'list'
58 + redirect_to :action => 'index'
60 else
59 else
61 render :action => 'new'
60 render :action => 'new'
62 end
61 end
@@ -66,7 +65,7
66 @user = User.find(params[:id])
65 @user = User.find(params[:id])
67 @user.last_ip = nil
66 @user.last_ip = nil
68 @user.save
67 @user.save
69 - redirect_to action: 'list', page: params[:page]
68 + redirect_to action: 'index', page: params[:page]
70 end
69 end
71
70
72 def create_from_list
71 def create_from_list
@@ -114,7 +113,7
114 flash[:notice] = 'User(s) ' + note.join(', ') +
113 flash[:notice] = 'User(s) ' + note.join(', ') +
115 ' were successfully created. ' +
114 ' were successfully created. ' +
116 '( (+) - created with random passwords.)'
115 '( (+) - created with random passwords.)'
117 - redirect_to :action => 'list'
116 + redirect_to :action => 'index'
118 end
117 end
119
118
120 def edit
119 def edit
@@ -133,7 +132,7
133
132
134 def destroy
133 def destroy
135 User.find(params[:id]).destroy
134 User.find(params[:id]).destroy
136 - redirect_to :action => 'list'
135 + redirect_to :action => 'index'
137 end
136 end
138
137
139 def user_stat
138 def user_stat
@@ -200,7 +199,7
200 def import
199 def import
201 if params[:file]==''
200 if params[:file]==''
202 flash[:notice] = 'Error importing no file'
201 flash[:notice] = 'Error importing no file'
203 - redirect_to :action => 'list' and return
202 + redirect_to :action => 'index' and return
204 end
203 end
205 import_from_file(params[:file])
204 import_from_file(params[:file])
206 end
205 end
@@ -253,7 +252,7
253 if user and contest
252 if user and contest
254 user.contests << contest
253 user.contests << contest
255 end
254 end
256 - redirect_to :action => 'list'
255 + redirect_to :action => 'index'
257 end
256 end
258
257
259 def remove_from_contest
258 def remove_from_contest
@@ -262,7 +261,7
262 if user and contest
261 if user and contest
263 user.contests.delete(contest)
262 user.contests.delete(contest)
264 end
263 end
265 - redirect_to :action => 'list'
264 + redirect_to :action => 'index'
266 end
265 end
267
266
268 def contest_management
267 def contest_management
@@ -133,6 +133,24
133 problem.each_value { |v| @summary[:solve] += 1 if v == 1 }
133 problem.each_value { |v| @summary[:solve] += 1 if v == 1 }
134 end
134 end
135
135
136 + def toggle_activate
137 + @user = User.find(params[:id])
138 + @user.update_attributes( activated: !@user.activated? )
139 + respond_to do |format|
140 + format.js { render partial: 'toggle_button',
141 + locals: {button_id: "#toggle_activate_user_#{@user.id}",button_on: @user.activated? } }
142 + end
143 + end
144 +
145 + def toggle_enable
146 + @user = User.find(params[:id])
147 + @user.update_attributes( enabled: !@user.enabled? )
148 + respond_to do |format|
149 + format.js { render partial: 'toggle_button',
150 + locals: {button_id: "#toggle_enable_user_#{@user.id}",button_on: @user.enabled? } }
151 + end
152 + end
153 +
136 protected
154 protected
137
155
138 def verify_online_registration
156 def verify_online_registration
@@ -192,4 +210,5
192 admin_authorization
210 admin_authorization
193 end
211 end
194
212
213 +
195 end
214 end
@@ -1,6 +1,38
1 # Methods added to this helper will be available to all templates in the application.
1 # Methods added to this helper will be available to all templates in the application.
2 module ApplicationHelper
2 module ApplicationHelper
3
3
4 + def navbar_user_header
5 + left_menu = ''
6 + right_menu = ''
7 + user = User.find(session[:user_id])
8 +
9 + if (user!=nil) and (GraderConfiguration.show_tasks_to?(user))
10 + left_menu << add_menu("#{I18n.t 'menu.tasks'}", 'tasks', 'list')
11 + left_menu << add_menu("#{I18n.t 'menu.submissions'}", 'main', 'submission')
12 + left_menu << add_menu("#{I18n.t 'menu.test'}", 'test', 'index')
13 + end
14 +
15 + if GraderConfiguration['right.user_hall_of_fame']
16 + left_menu << add_menu("#{I18n.t 'menu.hall_of_fame'}", 'report', 'problem_hof')
17 + end
18 +
19 + right_menu << add_menu("#{content_tag(:span,'',class: 'glyphicon glyphicon-question-sign')}".html_safe, 'main', 'help')
20 + right_menu << add_menu("#{content_tag(:span,'',class: 'glyphicon glyphicon-comment')}".html_safe, 'messages', 'list', {title: I18n.t('menu.messages'), data: {toggle: 'tooltip'}})
21 + if GraderConfiguration['system.user_setting_enabled']
22 + right_menu << add_menu("#{content_tag(:span,'',class: 'glyphicon glyphicon-cog')}".html_safe, 'users', 'index', {title: I18n.t('menu.settings'), data: {toggle: 'tooltip'}})
23 + end
24 + right_menu << add_menu("#{content_tag(:span,'',class: 'glyphicon glyphicon-log-out')} #{user.full_name}".html_safe, 'main', 'login', {title: I18n.t('menu.log_out'), data: {toggle: 'tooltip'}})
25 +
26 +
27 + result = content_tag(:ul,left_menu.html_safe,class: 'nav navbar-nav') + content_tag(:ul,right_menu.html_safe,class: 'nav navbar-nav navbar-right')
28 + end
29 +
30 + def add_menu(title, controller, action,html_option = {})
31 + link_option = {controller: controller, action: action}
32 + html_option[:class] = (html_option[:class] || '') + " active" if current_page?(link_option)
33 + content_tag(:li, link_to(title,link_option),html_option)
34 + end
35 +
4 def user_header
36 def user_header
5 menu_items = ''
37 menu_items = ''
6 user = User.find(session[:user_id])
38 user = User.find(session[:user_id])
@@ -75,6 +107,34
75 end
107 end
76 end
108 end
77
109
110 + def toggle_button(on,toggle_url,id, option={})
111 + btn_size = option[:size] || 'btn-xs'
112 + link_to (on ? "Yes" : "No"), toggle_url,
113 + {class: "btn btn-block #{btn_size} btn-#{on ? 'success' : 'default'} ajax-toggle",
114 + id: id,
115 + data: {remote: true, method: 'get'}}
116 + end
117 +
118 + def get_ace_mode(language)
119 + # return ace mode string from Language
120 +
121 + case language.pretty_name
122 + when 'Pascal'
123 + 'ace/mode/pascal'
124 + when 'C++','C'
125 + 'ace/mode/c_cpp'
126 + when 'Ruby'
127 + 'ace/mode/ruby'
128 + when 'Python'
129 + 'ace/mode/python'
130 + when 'Java'
131 + 'ace/mode/java'
132 + else
133 + 'ace/mode/c_cpp'
134 + end
135 + end
136 +
137 +
78 def user_title_bar(user)
138 def user_title_bar(user)
79 header = ''
139 header = ''
80 time_left = ''
140 time_left = ''
@@ -61,6 +61,10
61 result[:total_sub] = Submission.where(problem_id: self.id).count
61 result[:total_sub] = Submission.where(problem_id: self.id).count
62 result[:attempted_user] = Submission.where(problem_id: self.id).group_by(:user_id)
62 result[:attempted_user] = Submission.where(problem_id: self.id).group_by(:user_id)
63 end
63 end
64 +
65 + def long_name
66 + "[#{name}] #{full_name}"
67 + end
64
68
65 protected
69 protected
66
70
@@ -239,7 +239,7
239
239
240 def update_start_time
240 def update_start_time
241 stat = self.contest_stat
241 stat = self.contest_stat
242 - if stat == nil or stat.started_at == nil
242 + if (stat.nil?) or (stat.started_at.nil?)
243 stat ||= UserContestStat.new(:user => self)
243 stat ||= UserContestStat.new(:user => self)
244 stat.started_at = Time.now.gmtime
244 stat.started_at = Time.now.gmtime
245 stat.save
245 stat.save
@@ -1,5 +1,5
1 - - content_for :header do
1 + /- content_for :header do
2 - = javascript_include_tag 'local_jquery'
2 + / = javascript_include_tag 'local_jquery'
3
3
4 %h1 System configuration
4 %h1 System configuration
5
5
@@ -13,9 +13,11
13 - @grader_configuration = conf
13 - @grader_configuration = conf
14 %tr{:class => cycle("info-odd", "info-even")}
14 %tr{:class => cycle("info-odd", "info-even")}
15 %td
15 %td
16 - = in_place_editor_field :grader_configuration, :key, {}, :rows=>1
16 + /= in_place_editor_field :grader_configuration, :key, {}, :rows=>1
17 + = @grader_configuration.key
17 %td
18 %td
18 - = in_place_editor_field :grader_configuration, :value_type, {}, :rows=>1
19 + /= in_place_editor_field :grader_configuration, :value_type, {}, :rows=>1
20 + = @grader_configuration.value_type
19 %td
21 %td
20 = best_in_place @grader_configuration, :value, ok_button: "ok", cancel_button: "cancel"
22 = best_in_place @grader_configuration, :value, ok_button: "ok", cancel_button: "cancel"
21 %td= conf.description
23 %td= conf.description
@@ -2,10 +2,10
2 %td= grader.host
2 %td= grader.host
3 %td= grader.pid
3 %td= grader.pid
4 %td= grader.mode
4 %td= grader.mode
5 - %td= grader.updated_at.strftime("%H:%M:%S") if grader.updated_at!=nil
5 + %td= grader.updated_at.strftime("%H:%M:%S") unless grader.updated_at.nil?
6 %td= grader.task_type
6 %td= grader.task_type
7 %td
7 %td
8 - - if grader.task_id==nil
8 + - if grader.task_id.nil?
9 idle
9 idle
10 - else
10 - else
11 = link_to "#{grader.task_id}", :action => 'view', :id => grader.task_id, :type => grader.task_type
11 = link_to "#{grader.task_id}", :action => 'view', :id => grader.task_id, :type => grader.task_type
@@ -1,5 +1,5
1 - if grader_list.length!=0
1 - if grader_list.length!=0
2 - %table.graders
2 + %table.table.table-striped.table-condensed
3 %tr
3 %tr
4 %th host
4 %th host
5 %th pid
5 %th pid
@@ -7,6 +7,7
7 %th last updated
7 %th last updated
8 %th type
8 %th type
9 %th task
9 %th task
10 + %th
10 - grader_list.each do |grader|
11 - grader_list.each do |grader|
11 - if grader.active
12 - if grader.active
12 - c = 'active'
13 - c = 'active'
@@ -16,9 +17,9
16 = render :partial => 'grader', :locals => {:grader => grader}
17 = render :partial => 'grader', :locals => {:grader => grader}
17 - if not grader.terminated
18 - if not grader.terminated
18 - if GraderScript.grader_control_enabled?
19 - if GraderScript.grader_control_enabled?
19 - %td= link_to 'stop', {:action => 'stop', :id => grader}
20 + %td= link_to 'stop', {:action => 'stop', :id => grader}, class: 'btn btn-danger btn-xs btn-block'
20 - else
21 - else
21 - %td= link_to 'clear', {:action => 'clear', :id => grader}
22 + %td= link_to 'clear', {:action => 'clear', :id => grader}, class: 'btn btn-danger btn-xs btn-block'
22 - else
23 - else
23 %ul
24 %ul
24 %li None
25 %li None
@@ -1,12 +1,19
1 - content_for :head do
1 - content_for :head do
2 - = stylesheet_link_tag 'graders'
3 - = javascript_include_tag 'local_jquery'
4 <meta http-equiv ="refresh" content="60"/>
2 <meta http-equiv ="refresh" content="60"/>
5
3
6 %h1 Grader information
4 %h1 Grader information
7
5
8 - = link_to '[Refresh]', :action => 'list'
6 + %p
9 - %br/
7 + = link_to 'Refresh', { :action => 'list' }, class: 'btn btn-info'
8 +
9 + .panel.panel-primary
10 + .panel-heading
11 + Grader control:
12 + .panel-body
13 + =link_to 'Start Graders in grading env', { action: 'start_grading'}, class: 'btn btn-default', method: 'post'
14 + =link_to 'Start Graders in exam env', { action: 'start_exam'}, class: 'btn btn-default', method: 'post'
15 + =link_to 'Stop all running Graders', { action: 'stop_all'}, class: 'btn btn-default', method: 'post'
16 + =link_to 'Clear all data', { action: 'clear_all'}, class: 'btn btn-default', method: 'post'
10
17
11 .submitbox
18 .submitbox
12 .item
19 .item
@@ -25,49 +32,50
25 = submit_tag 'Clear all data'
32 = submit_tag 'Clear all data'
26 %br{:style => 'clear:both'}/
33 %br{:style => 'clear:both'}/
27
34
28 - %div{style: 'width:500px; float: left;'}
35 + .row
29 - - if @last_task
36 + .col-md-6
30 - Last task:
37 + - if @last_task
31 - = link_to "#{@last_task.id}", :action => 'view', :id => @last_task.id, :type => 'Task'
38 + Last task:
39 + = link_to "#{@last_task.id}", :action => 'view', :id => @last_task.id, :type => 'Task'
32
40
33 - %br/
41 + %br/
34
42
35 - - if @last_test_request
43 + - if @last_test_request
36 - Last test_request:
44 + Last test_request:
37 - = link_to "#{@last_test_request.id}", :action => 'view', :id => @last_test_request.id, :type => 'TestRequest'
45 + = link_to "#{@last_test_request.id}", :action => 'view', :id => @last_test_request.id, :type => 'TestRequest'
38
46
39 - %h2 Current graders
47 + %h2 Current graders
40
48
41 - = render :partial => 'grader_list', :locals => {:grader_list => @grader_processes}
49 + = render :partial => 'grader_list', :locals => {:grader_list => @grader_processes}
42
50
43 - %h2 Stalled graders
51 + %h2 Stalled graders
44
52
45 - = render :partial => 'grader_list', :locals => {:grader_list => @stalled_processes}
53 + = render :partial => 'grader_list', :locals => {:grader_list => @stalled_processes}
46
54
47 - %h2 Terminated graders
55 + %h2 Terminated graders
48
56
49 - = form_for :clear, :url => {:action => 'clear_terminated'} do |f|
57 + %p= link_to 'Clear data for terminated graders', { action: 'clear_terminated'}, class: 'btn btn-default', method: 'post'
50 - = submit_tag 'Clear data for terminated graders'
51
58
52 - = render :partial => 'grader_list', :locals => {:grader_list => @terminated_processes}
59 + = render :partial => 'grader_list', :locals => {:grader_list => @terminated_processes}
53 - %div{}
60 + .col-md-6
54 - %h2 Last 20 submissions
61 + %h2 Last 20 submissions
55 - %table.graders
62 + %table.table.table-striped.table-condensed
56 - %thead
63 + %thead
57 - %th ID
64 + %th ID
58 - %th User
65 + %th User
59 - %th Problem
66 + %th Problem
60 - %th Submitted
67 + %th Submitted
61 - %th Graded
68 + %th Graded
62 - %th Result
69 + %th Result
63 - %tbody
70 + %th
64 - - @submission.each do |sub|
71 + %tbody
65 - %tr.inactive
72 + - @submission.each do |sub|
66 - %td= link_to sub.id, controller: 'graders' ,action: 'submission', id: sub.id
73 + %tr.inactive
67 - %td= sub.try(:user).try(:full_name)
74 + %td= link_to sub.id, controller: 'graders' ,action: 'submission', id: sub.id
68 - %td= sub.try(:problem).try(:full_name)
75 + %td= sub.try(:user).try(:full_name)
69 - %td= "#{time_ago_in_words(sub.submitted_at)} ago"
76 + %td= sub.try(:problem).try(:full_name)
70 - %td= sub.graded_at ? "#{time_ago_in_words(sub.graded_at)} ago" : " "
77 + %td= "#{time_ago_in_words(sub.submitted_at)} ago"
71 - %td= sub.grader_comment
78 + %td= sub.graded_at ? "#{time_ago_in_words(sub.graded_at)} ago" : " "
79 + %td= sub.grader_comment
72
80
73
81
@@ -1,67 +1,90
1 - %style{type: "text/css"}
1 + //%style{type: "text/css"}
2 - = @css_style
2 + // = @css_style
3 - :css
4 - .field {
5 - font-weight: bold;
6 - text-align: right;
7 - padding: 3px;
8 - }
9 -
10
3
11 %h1= "Submission: #{@submission.id}"
4 %h1= "Submission: #{@submission.id}"
12
5
13 -
6 + %textarea#data{style: "display:none;"}
14 - %h2 Stat
7 + :preserve
8 + #{@submission.source}
15
9
16 - %table.info
10 + //%div.highlight{:style => "border: 1px solid black;"}
17 - %thead
11 + //=@formatted_code.html_safe
18 - %tr.info-head
12 + .containter
19 - %th Field
13 + .row
20 - %th Value
14 + .col-md-7
21 - %tbody
15 + %h2 Source Code
22 - %tr{class: cycle('info-even','info-odd')}
16 + .col-md-5
23 - %td.field User:
17 + %h2 Stat
24 - %td.value
18 + .row
25 - - if @submission.user
19 + .col-md-7
26 - = link_to "(#{@submission.user.login})", controller: "users", action: "profile", id: @submission.user
20 + %div#editor{ style: "font-size: 14px; height: 400px; border-radius:5px;" }
27 - = @submission.user.full_name
21 + :javascript
28 - - else
22 + e = ace.edit("editor")
29 - = "(n/a)"
23 + e.setOptions({ maxLines: Infinity })
30 - %tr{class: cycle('info-even','info-odd')}
24 + e.setValue($("#data").text())
31 - %td.field Problem:
25 + e.gotoLine(1)
32 - %td.value
26 + e.getSession().setMode("#{get_ace_mode(@submission.language)}")
33 - - if @submission.problem!=nil
27 + e.setReadOnly(true)
34 - = link_to "(#{@submission.problem.name})", controller: "problems", action: "stat", id: @submission.problem
28 + .col-md-5
35 - = @submission.problem.full_name
29 + %table.table.table-striped
36 - - else
30 + %tr
37 - = "(n/a)"
31 + %td.text-right
38 - %tr{class: cycle('info-even','info-odd')}
32 + %strong User
39 - %td.field Tries:
33 + %td
40 - %td.value= @submission.number
34 + - if @submission.user
41 - %tr{class: cycle('info-even','info-odd')}
35 + = link_to "(#{@submission.user.login})", controller: "users", action: "profile", id: @submission.user
42 - %td.field Submitted:
36 + = @submission.user.full_name
43 - %td.value #{time_ago_in_words(@submission.submitted_at)} ago (at #{@submission.submitted_at.to_formatted_s(:long)})
37 + - else
44 - %tr{class: cycle('info-even','info-odd')}
38 + = "(n/a)"
45 - %td.field Graded:
39 + %tr
46 - %td.value #{time_ago_in_words(@submission.graded_at)} ago (at #{@submission.graded_at.to_formatted_s(:long)})
40 + %td.text-right
47 - %tr{class: cycle('info-even','info-odd')}
41 + %strong Task
48 - %td.field Points:
42 + %td
49 - %td.value #{@submission.points}/#{@submission.problem.full_score}
43 + - if @submission.problem!=nil
50 - %tr{class: cycle('info-even','info-odd')}
44 + = link_to "(#{@submission.problem.name})", controller: "problems", action: "stat", id: @submission.problem
51 - %td.field Comment:
45 + = @submission.problem.full_name
52 - %td.value #{@submission.grader_comment}
46 + - else
53 - %tr{class: cycle('info-even','info-odd')}
47 + = "(n/a)"
54 - %td.field Runtime (s):
48 + %tr
55 - %td.value #{@submission.max_runtime}
49 + %td.text-right
56 - %tr{class: cycle('info-even','info-odd')}
50 + %strong Tries
57 - %td.field Memory (kb):
51 + %td= @submission.number
58 - %td.value #{@submission.peak_memory}
52 + %tr
59 - - if session[:admin]
53 + %td.text-right
60 - %tr{class: cycle('info-even','info-odd')}
54 + %strong Language
61 - %td.field IP:
55 + %td= @submission.language.pretty_name
62 - %td.value #{@submission.ip_address}
56 + %tr
57 + %td.text-right
58 + %strong Submitted
59 + %td #{time_ago_in_words(@submission.submitted_at)} ago (at #{@submission.submitted_at.to_formatted_s(:long)})
60 + %tr
61 + %td.text-right
62 + %strong Graded
63 + - if @submission.graded_at
64 + %td #{time_ago_in_words(@submission.graded_at)} ago (at #{@submission.graded_at.to_formatted_s(:long)})
65 + - else
66 + %td -
67 + %tr
68 + %td.text-right
69 + %strong Points
70 + %td #{@submission.points}/#{@submission.problem.full_score}
71 + %tr
72 + %td.text-right
73 + %strong Comment
74 + %td #{@submission.grader_comment}
75 + %tr
76 + %td.text-right
77 + %strong Runtime (s)
78 + %td #{@submission.max_runtime}
79 + %tr
80 + %td.text-right
81 + %strong Memory (kb)
82 + %td #{@submission.peak_memory}
83 + - if session[:admin]
84 + %tr
85 + %td.text-right
86 + %strong IP
87 + %td #{@submission.ip_address}
63
88
64 - %h2 Source code
65 - //%div.highlight{:style => "border: 1px solid black;"}
66 - =@formatted_code.html_safe
67
89
90 +
@@ -1,19 +1,13
1 - .announcement{:id => "announcement-#{announcement.id}", :style => "#{'display: none; opacity: 0' if (defined? announcement_effect) and announcement_effect }"}
1 + %li.list-group-item
2 - %div
2 + %strong
3 - .announcement-title
3 + = announcement.title
4 - -# .toggles
4 + %small= "(updated #{time_ago_in_words(announcement.updated_at)} ago on #{announcement.updated_at})"
5 - -# %a{:href => '#', :onclick => "$(\"announcement-body-#{announcement.id}\").blindUp({duration: 0.2}); return false;"}
5 +
6 - -# [hide]
6 + %br
7 - -# %a{:href => '#', :onclick => "$(\"announcement-body-#{announcement.id}\").blindDown({duration: 0.2}); return false;"}
7 + = markdown(announcement.body)
8 - -# [show]
8 + :javascript
9 - = announcement.title
9 + Announcement.updateRecentId(#{announcement.id});
10 - .announcement-body{:id => "announcement-body-#{announcement.id}"}
10 + - if (defined? announcement_effect) and announcement_effect
11 - = markdown(announcement.body)
12 - -#.pub-info
13 - -# %p= "#{announcement.author}, #{announcement.created_at}"
14 :javascript
11 :javascript
15 - Announcement.updateRecentId(#{announcement.id});
12 + $("announcement-#{announcement.id}").blindDown({duration: 0.2});
16 - - if (defined? announcement_effect) and announcement_effect
13 + $("announcement-#{announcement.id}").appear({duration: 0.5, queue: 'end'});
17 - :javascript
18 - $("announcement-#{announcement.id}").blindDown({duration: 0.2});
19 - $("announcement-#{announcement.id}").appear({duration: 0.5, queue: 'end'});
@@ -1,18 +1,18
1
1
2 - %tr{:class => ((submission_counter%2==0) ? "info-even" : "info-odd")}
2 + %tr
3 - %td.info{:align => "center"}
3 + %td{:align => "center"}
4 = submission_counter+1
4 = submission_counter+1
5 - %td.info{:align => "center"}
5 + %td{:align => "center"}
6 = link_to "##{submission.id}", controller: :graders, action: :submission, id: submission.id
6 = link_to "##{submission.id}", controller: :graders, action: :submission, id: submission.id
7 - %td.info
7 + %td
8 = l submission.submitted_at, format: :long
8 = l submission.submitted_at, format: :long
9 = "( #{time_ago_in_words(submission.submitted_at)} ago)"
9 = "( #{time_ago_in_words(submission.submitted_at)} ago)"
10 - %td.info{:align => "center"}
10 + %td
11 = submission.source_filename
11 = submission.source_filename
12 = " (#{submission.language.pretty_name}) "
12 = " (#{submission.language.pretty_name}) "
13 = link_to('[load]',{:action => 'source', :id => submission.id})
13 = link_to('[load]',{:action => 'source', :id => submission.id})
14 - %td.info
14 + %td
15 - - if submission.graded_at!=nil
15 + - if submission.graded_at
16 = "Graded at #{format_short_time(submission.graded_at)}."
16 = "Graded at #{format_short_time(submission.graded_at)}."
17 %br/
17 %br/
18 = "Score: #{(submission.points*100/submission.problem.full_score).to_i} " if GraderConfiguration['ui.show_score']
18 = "Score: #{(submission.points*100/submission.problem.full_score).to_i} " if GraderConfiguration['ui.show_score']
@@ -20,5 +20,7
20 %tt
20 %tt
21 = submission.grader_comment
21 = submission.grader_comment
22 = "]"
22 = "]"
23 - %td.info
23 + %td
24 = render :partial => 'compiler_message', :locals => {:compiler_message => submission.compiler_message }
24 = render :partial => 'compiler_message', :locals => {:compiler_message => submission.compiler_message }
25 + %td
26 + = link_to 'Edit', direct_edit_submission_path(submission.id), class: 'btn btn-success'
@@ -1,8 +1,8
1
1
2 - - if submission==nil
2 + - if submission.nil?
3 = "-"
3 = "-"
4 - else
4 - else
5 - - if submission.graded_at==nil
5 + - if submission.graded_at.nil?
6 =t 'main.submitted_at'
6 =t 'main.submitted_at'
7 = format_short_time(submission.submitted_at.localtime)
7 = format_short_time(submission.submitted_at.localtime)
8 - else
8 - else
@@ -22,5 +22,5
22 = link_to("[#{t 'main.cmp_msg'}]", {:action => 'compiler_msg', :id => submission.id}, {:popup => true})
22 = link_to("[#{t 'main.cmp_msg'}]", {:action => 'compiler_msg', :id => submission.id}, {:popup => true})
23 = " | "
23 = " | "
24 = link_to("[#{t 'main.src_link'}]",{:action => 'source', :id => submission.id})
24 = link_to("[#{t 'main.src_link'}]",{:action => 'source', :id => submission.id})
25 - = " | "
25 + //= " | "
26 - = link_to "[#{t 'main.submissions_link'}]", :action => 'submission', :id => problem_name
26 + //= link_to "[#{t 'main.submissions_link'}]", main_submission_path(submission.problem.id)
@@ -3,49 +3,48
3
3
4 = user_title_bar(@user)
4 = user_title_bar(@user)
5
5
6 - .announcementbox{:style => (@announcements.length==0 ? "display:none" : "")}
7 - %span{:class => 'title'}
8 - Announcements
9 - #announcementbox-body
10 - = render :partial => 'announcement', :collection => @announcements
11 -
12 - - if GraderConfiguration.show_submitbox_to?(@user)
13 - .submitbox
14 - = error_messages_for 'submission'
15 - = render :partial => 'submission_box'
16 -
17 -
18 - %hr/
19 -
20 - if (GraderConfiguration.contest_mode?) and (@user.site!=nil) and (@user.site.started!=true)
6 - if (GraderConfiguration.contest_mode?) and (@user.site!=nil) and (@user.site.started!=true)
21 %p=t 'main.start_soon'
7 %p=t 'main.start_soon'
22
8
23 - - if GraderConfiguration.show_tasks_to?(@user)
9 + .row
24 - - if not GraderConfiguration.multicontests?
10 + .col-md-7
25 - %table.info
11 + - if GraderConfiguration.show_submitbox_to?(@user)
26 - %tr.info-head
12 + .panel.panel-primary
27 - %th
13 + .panel-heading
28 - %th Tasks name
14 + Submission
29 - %th Full name
15 + .panel-body
30 - %th # of sub(s)
16 + = render :partial => 'submission_box'
31 - %th Results
17 + - if GraderConfiguration.show_tasks_to?(@user)
32 - = render :partial => 'problem', :collection => @problems
18 + - if not GraderConfiguration.multicontests?
33 - - else
19 + %table.table.table-striped.table-condensed
34 - - @contest_problems.each do |cp|
20 + %thead
35 - - if cp[:problems].length > 0
21 + %tr
36 - %h2{:class =>'contest-title'}
22 + %th Task name
37 - = "#{cp[:contest] ? cp[:contest].title : 'Public problems'}"
23 + %th Full name
38 - %table.info
24 + %th # of sub(s)
39 - %tr.info-head
25 + %th Results
40 - %th
26 + %th
41 - %th Tasks name
27 + %tbody
42 - %th Full name
28 + = render :partial => 'problem', :collection => @problems
43 - %th # of sub(s)
29 + - else
44 - %th Results
30 + - @contest_problems.each do |cp|
45 - = render :partial => 'problem', :collection => cp[:problems]
31 + - if cp[:problems].length > 0
46 -
32 + %h2{:class =>'contest-title'}
47 -
33 + = "#{cp[:contest] ? cp[:contest].title : 'Public problems'}"
48 - %hr/
34 + %table.info
35 + %tr.info-head
36 + %th Task name
37 + %th Full name
38 + %th # of sub(s)
39 + %th Results
40 + %th
41 + = render :partial => 'problem', :collection => cp[:problems]
42 + .col-md-5
43 + .panel.panel-info
44 + .panel-heading
45 + Announcement
46 + %ul.list-group
47 + = render :partial => 'announcement', :collection => @announcements
49
48
50 %script{:type => 'text/javascript'}
49 %script{:type => 'text/javascript'}
51 = "Announcement.refreshUrl = '#{url_for :controller => 'main', :action => 'announcements'}';"
50 = "Announcement.refreshUrl = '#{url_for :controller => 'main', :action => 'announcements'}';"
@@ -1,25 +1,31
1 = user_title_bar(@user)
1 = user_title_bar(@user)
2
2
3 - .task-menu
3 + .panel.panel-info
4 - Task List
4 + .panel-heading
5 - %br/
5 + Select Problems
6 - - @problems.each do |problem|
6 + .panel-body
7 - = link_to problem.name, :action => 'submission', :id => problem.name
7 + .form-inline
8 + = select 'submission',
9 + 'problem_id',
10 + @problems.collect {|p| ["[#{p.name}] #{p.full_name}", main_submission_url(p.id)]},
11 + { selected: (@problem ? main_submission_url(@problem) : -1) },
12 + { class: 'select2 form-control'}
13 + %button.btn.btn-primary.btn-sm.go-button#problem_go{data: {source: '#submission_problem_id'}} Go
8
14
9 - if @problem!=nil
15 - if @problem!=nil
10 %h2= "Task: #{@problem.full_name} (#{@problem.name})"
16 %h2= "Task: #{@problem.full_name} (#{@problem.name})"
11
17
12 - if @submissions!=nil
18 - if @submissions!=nil
13 - if @submissions.length>0
19 - if @submissions.length>0
14 - %table.info
20 + %table.table
15 - %tr.info-head
21 + %thead
16 - %th.info No.
22 + %th No.
17 - %th.info #
23 + %th #
18 - %th.info At
24 + %th At
19 - %th.info Source
25 + %th Source
20 - %th.info Result
26 + %th Result
21 - %th.info{:width => "300px"}
27 + %th{:width => "300px"} Compiler message
22 - Compiler message
28 + %th
23 = render :partial => 'submission', :collection => @submissions
29 = render :partial => 'submission', :collection => @submissions
24 - else
30 - else
25 No submission
31 No submission
@@ -1,14 +1,3
1 - - content_for :header do
2 - = javascript_include_tag 'local_jquery'
3 -
4 - :javascript
5 - $(document).ready( function() {
6 - $("#mem_remark").hover( function() {
7 - $("#mem_remark_box").show();
8 - }, function() {
9 - $("#mem_remark_box").hide();
10 - });
11 - });
12 :css
1 :css
13 .hof_user { color: orangered; font-style: italic; }
2 .hof_user { color: orangered; font-style: italic; }
14 .hof_language { color: green; font-style: italic; }
3 .hof_language { color: green; font-style: italic; }
@@ -34,94 +23,114
34 overflow: auto;
23 overflow: auto;
35 }
24 }
36
25
37 - %h1 (#{Problem.find(params[:id]).name}) #{Problem.find(params[:id]).full_name}
38
26
39 - %h2 Problem Stat
27 + .container
40 - %table.info
28 + .row
41 - %thead
29 + .col-md-4
42 - %tr.info-head
30 + %h2 Overall Stat
43 - %th Stat
31 + %table.table.table-hover
44 - %th Value
32 + %thead
45 - %tbody
33 + %tr
46 - %tr{class: cycle('info-even','info-odd')}
34 + %th
47 - %td.info_param Submissions
35 + %th
48 - %td= @summary[:count]
36 + %tbody
49 - %tr{class: cycle('info-even','info-odd')}
37 + %tr
50 - %td.info_param Solved/Attempted User
38 + %td.info_param Submissions
51 - %td #{@summary[:solve]}/#{@summary[:attempt]} (#{(@summary[:solve]*100.0/@summary[:attempt]).round(1)}%)
39 + %td= @summary[:count]
52 - - if @best
40 + %tr
53 - %tr{class: cycle('info-even','info-odd')}
41 + %td.info_param Solved/Attempted User
54 - %td.info_param Best Runtime
42 + %td #{@summary[:solve]}/#{@summary[:attempt]} (#{(@summary[:solve]*100.0/@summary[:attempt]).round(1)}%)
55 - %td
43 + - if @best
56 - by #{link_to @best[:runtime][:user], controller:'users', action:'profile', id:@best[:memory][:user_id]}
44 + %tr
57 - using <span class="hof_language">#{@best[:runtime][:lang]}</span>
45 + %td.info_param Best Runtime
58 - with <span class="hof_value">#{@best[:runtime][:value] * 1000} milliseconds</span>
46 + %td
59 - at submission
47 + by #{link_to @best[:runtime][:user], controller:'users', action:'profile', id:@best[:memory][:user_id]}
60 - = link_to("#" + @best[:runtime][:sub_id].to_s, controller: 'graders', action: 'submission', id:@best[:runtime][:sub_id])
48 + %br
49 + using <span class="text-success">#{@best[:runtime][:lang]}</span>
50 + %br
51 + with <span class="text-success">#{@best[:runtime][:value] * 1000} milliseconds</span>
52 + %br
53 + at submission
54 + = link_to("#" + @best[:runtime][:sub_id].to_s, controller: 'graders', action: 'submission', id:@best[:runtime][:sub_id])
61
55
62 - %tr{class: cycle('info-even','info-odd')}
56 + %tr
63 - %td.info_param
57 + %td.info_param
64 - Best Memory Usage
58 + Best Memory Usage
65 - %sup{ id: "mem_remark", style: "position:relative; color: blue;"}
59 + %sup{ id: "xmem_remark",
66 - [?]
60 + style: "position:relative; color: blue;",
67 - %span.tooltip#mem_remark_box
61 + data: {toggle: 'tooltip', placement: 'top', animation: 'false', delay: 20},
68 - This counts only for submission with 100% score.
62 + title: "This counts only for submission with 100% score. Right now, java is excluded from memory usage competition. (Because it always uses 2GB memory...)"}
69 - Right now, java is excluded from memory usage competition. (Because it always uses 2GB memory...)
63 + [?]
70 - %td
64 + %td
71 - by #{link_to @best[:memory][:user], controller:'users', action:'profile', id:@best[:memory][:user_id]}
65 + by #{link_to @best[:memory][:user], controller:'users', action:'profile', id:@best[:memory][:user_id]}
72 - using <span class="hof_language">#{@best[:memory][:lang]}</span>
66 + %br
73 - with <span class="hof_value">#{number_with_delimiter(@best[:memory][:value])} kbytes </span>
67 + using <span class="text-success">#{@best[:memory][:lang]}</span>
74 - at submission
68 + %br
75 - = link_to("#" + @best[:memory][:sub_id].to_s, controller: 'graders' , action: 'submission', id:@best[:memory][:sub_id])
69 + with <span class="text-success">#{number_with_delimiter(@best[:memory][:value])} kbytes </span>
70 + %br
71 + at submission
72 + = link_to("#" + @best[:memory][:sub_id].to_s, controller: 'graders' , action: 'submission', id:@best[:memory][:sub_id])
76
73
77 - %tr{class: cycle('info-even','info-odd')}
74 + %tr
78 - %td.info_param Shortest Code
75 + %td.info_param Shortest Code
79 - %td
76 + %td
80 - by #{link_to @best[:length][:user], controller:'users', action:'profile', id:@best[:length][:user_id]}
77 + by #{link_to @best[:length][:user], controller:'users', action:'profile', id:@best[:length][:user_id]}
81 - using <span class="hof_language">#{@best[:length][:lang]}</span>
78 + %br
82 - with <span class="hof_value">#{@best[:length][:value]} bytes</span>
79 + using <span class="text-success">#{@best[:length][:lang]}</span>
83 - at submission
80 + %br
84 - = link_to("#" + @best[:length][:sub_id].to_s, controller: 'graders' , action: 'submission', id: @best[:length][:sub_id])
81 + with <span class="text-success">#{@best[:length][:value]} bytes</span>
85 -
82 + %br
86 - %tr{class: cycle('info-even','info-odd')}
83 + at submission
87 - %td.info_param First solver
84 + = link_to("#" + @best[:length][:sub_id].to_s, controller: 'graders' , action: 'submission', id: @best[:length][:sub_id])
88 - %td
89 - #{link_to @best[:first][:user], controller:'users', action:'profile', id:@best[:first][:user_id]} is the first solver
90 - using <span class="hof_language">#{@best[:first][:lang]}</span>
91 - on <span class="hof_value">#{@best[:first][:value]}</span>
92 - at submission
93 - = link_to("#" + @best[:first][:sub_id].to_s, controller: 'graders' , action: 'submission', id: @best[:first][:sub_id])
94 -
95 - - if @best
96 - %h2 By language
97
85
98 - %table.info
86 + %tr
99 - %thead
87 + %td.info_param First solver
100 - %tr.info-head
88 + %td
101 - %th Language
89 + - if @best[:first][:user] != '(NULL)'
102 - %th Best runtime (ms)
90 + #{link_to @best[:first][:user], controller:'users', action:'profile', id:@best[:first][:user_id]} is the first solver
103 - %th Best memory (kbytes)
91 + %br
104 - %th Shortest Code (bytes)
92 + using <span class="text-success">#{@best[:first][:lang]}</span>
105 - %th First solver
93 + %br
106 - %tbody
94 + on <span class="text-success">#{@best[:first][:value]}</span>
107 - - @by_lang.each do |lang,value|
95 + %br
108 - %tr{class: cycle('info-even','info-odd')}
96 + at submission
109 - %td= lang
97 + = link_to("#" + @best[:first][:sub_id].to_s, controller: 'graders' , action: 'submission', id: @best[:first][:sub_id])
110 - %td
98 + - else
111 - = link_to value[:runtime][:user], controller: 'users', action: 'profile', id: value[:runtime][:user_id]
99 + no first solver
112 - = "(#{(value[:runtime][:value] * 1000).to_i} @"
100 + .col-md-8
113 - = "#{link_to("#" + value[:runtime][:sub_id].to_s, controller: 'graders' , action: 'submission', id: value[:runtime][:sub_id])} )".html_safe
101 + - if @best
114 - %td
102 + %h2 By Language
115 - = link_to value[:memory][:user], controller: 'users', action: 'profile', id: value[:memory][:user_id]
103 + %table.table.table-hover
116 - = "(#{number_with_delimiter(value[:memory][:value])} @"
104 + %thead
117 - = "#{link_to("#" + value[:memory][:sub_id].to_s, controller: 'graders' , action: 'submission', id: value[:memory][:sub_id])} )".html_safe
105 + %tr
118 - %td
106 + %th Language
119 - = link_to value[:length][:user], controller: 'users', action: 'profile', id: value[:length][:user_id]
107 + %th Best runtime (ms)
120 - = "(#{value[:length][:value]} @"
108 + %th Best memory (kbytes)
121 - = "#{link_to("#" + value[:length][:sub_id].to_s, controller: 'graders' , action: 'submission', id: value[:length][:sub_id])} )".html_safe
109 + %th Shortest Code (bytes)
122 - %td
110 + %th First solver
123 - - if value[:first][:user] != '(NULL)' #TODO: i know... this is wrong...
111 + %tbody
124 - = link_to value[:first][:user], controller: 'users', action: 'profile', id: value[:first][:user_id]
112 + - @by_lang.each do |lang,value|
125 - = "(#{value[:first][:value]} @"
113 + %tr
126 - = "#{link_to("#" + value[:first][:sub_id].to_s, controller: 'graders' , action: 'submission', id: value[:first][:sub_id])} )".html_safe
114 + %td= lang
115 + %td
116 + = link_to value[:runtime][:user], controller: 'users', action: 'profile', id: value[:runtime][:user_id]
117 + %br
118 + = "(#{(value[:runtime][:value] * 1000).to_i} @"
119 + = "#{link_to("#" + value[:runtime][:sub_id].to_s, controller: 'graders' , action: 'submission', id: value[:runtime][:sub_id])} )".html_safe
120 + %td
121 + = link_to value[:memory][:user], controller: 'users', action: 'profile', id: value[:memory][:user_id]
122 + %br
123 + = "(#{number_with_delimiter(value[:memory][:value])} @"
124 + = "#{link_to("#" + value[:memory][:sub_id].to_s, controller: 'graders' , action: 'submission', id: value[:memory][:sub_id])} )".html_safe
125 + %td
126 + = link_to value[:length][:user], controller: 'users', action: 'profile', id: value[:length][:user_id]
127 + %br
128 + = "(#{value[:length][:value]} @"
129 + = "#{link_to("#" + value[:length][:sub_id].to_s, controller: 'graders' , action: 'submission', id: value[:length][:sub_id])} )".html_safe
130 + %td
131 + - if value[:first][:user] != '(NULL)' #TODO: i know... this is wrong...
132 + = link_to value[:first][:user], controller: 'users', action: 'profile', id: value[:first][:user_id]
133 + %br
134 + = "(#{value[:first][:value]} @"
135 + = "#{link_to("#" + value[:first][:sub_id].to_s, controller: 'graders' , action: 'submission', id: value[:first][:sub_id])} )".html_safe
127
136
@@ -5,19 +5,25
5 /- else
5 /- else
6 / %h1 All-Time Hall of Fame
6 / %h1 All-Time Hall of Fame
7
7
8 + .panel.panel-info
9 + .panel-heading
10 + Select Task
11 + .panel-body
12 + .form-inline
13 + = select 'report',
14 + 'problem_id',
15 + @problems.collect {|p| ["[#{p.name}] #{p.full_name}", report_problem_hof_url(p.id)]},
16 + {:selected => report_problem_hof_url(@problem)},
17 + { class: 'select2 form-control' }
18 + %button.btn.btn-primary.btn-sm.go-button#problem_go{data: {source: "#report_problem_id"}} Go
8
19
9 - %h1 Hall of Fame
10 - .task-menu
11 - Tasks
12 - %br/
13 - - @problems.each do |prob|
14 - = link_to( "[#{prob.name}]", {id: prob.id})
15
20
16 - unless params[:id]
21 - unless params[:id]
17 /=render partial: 'all_time_hof'
22 /=render partial: 'all_time_hof'
18 Please select a problem.
23 Please select a problem.
19 - else
24 - else
20 - =render partial: 'task_hof'
25 + %h1 [#{Problem.find(params[:id]).name}] #{Problem.find(params[:id]).full_name}
21 %h2 Submission History
26 %h2 Submission History
22 =render partial: 'application/bar_graph', locals: { histogram: @histogram }
27 =render partial: 'application/bar_graph', locals: { histogram: @histogram }
28 + =render partial: 'task_hof'
23
29
@@ -1,12 +1,12
1 - - content_for :header do
1 + /- content_for :header do
2 - = javascript_include_tag 'local_jquery'
2 + / = javascript_include_tag 'local_jquery'
3 - = stylesheet_link_tag 'tablesorter-theme.cafe'
3 + / = stylesheet_link_tag 'tablesorter-theme.cafe'
4
4
5 %script{:type=>"text/javascript"}
5 %script{:type=>"text/javascript"}
6 $(function () {
6 $(function () {
7 $('#since_datetime').datetimepicker({ showButtonPanel: true, dateFormat: "yy-mm-dd", controlType: "slider"} );
7 $('#since_datetime').datetimepicker({ showButtonPanel: true, dateFormat: "yy-mm-dd", controlType: "slider"} );
8 $('#until_datetime').datetimepicker({ showButtonPanel: true, dateFormat: "yy-mm-dd", controlType: "slider"} );
8 $('#until_datetime').datetimepicker({ showButtonPanel: true, dateFormat: "yy-mm-dd", controlType: "slider"} );
9 - $('#my_table').tablesorter({widgets: ['zebra']});
9 + /$('#my_table').tablesorter({widgets: ['zebra']});
10 });
10 });
11
11
12 %h1 User grading results
12 %h1 User grading results
@@ -26,22 +26,22
26 = link_to '[Show only latest submissions]', controller: :user_admin, action: :user_stat
26 = link_to '[Show only latest submissions]', controller: :user_admin, action: :user_stat
27 = link_to '[download csv with all problems]', controller: :user_admin, action: :user_stat_max, commit: 'download csv'
27 = link_to '[download csv with all problems]', controller: :user_admin, action: :user_stat_max, commit: 'download csv'
28
28
29 - %table.tablesorter-cafe#my_table
29 + %table.table.sortable.table-striped.table-bordered
30 %thead
30 %thead
31 %tr
31 %tr
32 - %th User
32 + %th Login
33 %th Name
33 %th Name
34 %th Activated?
34 %th Activated?
35 - %th Logged in
35 + %th Logged_in
36 %th Contest(s)
36 %th Contest(s)
37 %th Remark
37 %th Remark
38 - @problems.each do |p|
38 - @problems.each do |p|
39 - %th= p.name
39 + %th.text-right= p.name
40 - %th Total
40 + %th.text-right Total
41 - %th Passed
41 + %th.text-right Passed
42 %tbody
42 %tbody
43 - @scorearray.each do |sc|
43 - @scorearray.each do |sc|
44 - %tr{class: cycle('info-even','info-odd')}
44 + %tr
45 - total,num_passed = 0,0
45 - total,num_passed = 0,0
46 - sc.each_index do |i|
46 - sc.each_index do |i|
47 - if i == 0
47 - if i == 0
@@ -52,8 +52,10
52 %td= sc[i].contests.collect {|c| c.name}.join(', ')
52 %td= sc[i].contests.collect {|c| c.name}.join(', ')
53 %td= sc[i].remark
53 %td= sc[i].remark
54 - else
54 - else
55 - %td= sc[i][0]
55 + %td.text-right= sc[i][0]
56 - total += sc[i][0]
56 - total += sc[i][0]
57 - num_passed += 1 if sc[i][1]
57 - num_passed += 1 if sc[i][1]
58 - %td= total
58 + %td.text-right= total
59 - %td= num_passed
59 + %td.text-right= num_passed
60 + :javascript
61 + $.bootstrapSortable(true,'reversed')
@@ -59,7 +59,12
59 # Version of your assets, change this if you want to expire all your assets
59 # Version of your assets, change this if you want to expire all your assets
60 config.assets.version = '1.0'
60 config.assets.version = '1.0'
61
61
62 - config.assets.precompile += ['announcement_refresh.js','effects.js','site_update.js','graders.css','problems.css']
62 + config.assets.precompile += ['announcement_refresh.js','effects.js','site_update.js']
63 config.assets.precompile += ['local_jquery.js','tablesorter-theme.cafe.css']
63 config.assets.precompile += ['local_jquery.js','tablesorter-theme.cafe.css']
64 + %w( announcements configurations contests contest_management graders heartbeat
65 + login main messages problems report site sites sources tasks
66 + test user_admin users ).each do |controller|
67 + config.assets.precompile += ["#{controller}.js", "#{controller}.css"]
68 + end
64 end
69 end
65 end
70 end
@@ -36,5 +36,5
36 config.assets.debug = true
36 config.assets.debug = true
37
37
38 # Prevents assets from rendering twice
38 # Prevents assets from rendering twice
39 - config.serve_static_assets = false
39 + config.serve_static_assets = true
40 end
40 end
@@ -19,7 +19,7
19 messages: 'Messages'
19 messages: 'Messages'
20 tasks: 'Tasks'
20 tasks: 'Tasks'
21 submissions: 'Submissions'
21 submissions: 'Submissions'
22 - test: 'Test Interface'
22 + test: 'Test'
23 hall_of_fame: 'Hall of Fame'
23 hall_of_fame: 'Hall of Fame'
24 help: 'Help'
24 help: 'Help'
25 settings: 'Settings'
25 settings: 'Settings'
@@ -1,70 +1,59
1 CafeGrader::Application.routes.draw do
1 CafeGrader::Application.routes.draw do
2 - get "report/login"
2 + get "sources/direct_edit"
3 +
4 + root :to => 'main#login'
3
5
4 resources :contests
6 resources :contests
5
7
6 - resources :announcements
7 resources :sites
8 resources :sites
8
9
10 + resources :announcements do
11 + member do
12 + get 'toggle','toggle_front'
13 + end
14 + end
15 +
16 + resources :problems do
17 + member do
18 + get 'toggle'
19 + get 'toggle_test'
20 + end
21 + collection do
22 + get 'turn_all_off'
23 + get 'turn_all_on'
24 + get 'import'
25 + get 'manage'
26 + end
27 + end
28 +
9 resources :grader_configuration, controller: 'configurations'
29 resources :grader_configuration, controller: 'configurations'
10
30
11 - # The priority is based upon order of creation:
31 + resources :users do
12 - # first created -> highest priority.
32 + member do
13 -
33 + get 'toggle_activate', 'toggle_enable'
14 - # Sample of regular route:
34 + end
15 - # match 'products/:id' => 'catalog#view'
35 + end
16 - # Keep in mind you can assign values other than :controller and :action
17 -
18 - # Sample of named route:
19 - # match 'products/:id/purchase' => 'catalog#purchase', :as => :purchase
20 - # This route can be invoked with purchase_url(:id => product.id)
21 -
22 - # Sample resource route (maps HTTP verbs to controller actions automatically):
23 - # resources :products
24 -
25 - # Sample resource route with options:
26 - # resources :products do
27 - # member do
28 - # get 'short'
29 - # post 'toggle'
30 - # end
31 - #
32 - # collection do
33 - # get 'sold'
34 - # end
35 - # end
36
36
37 - # Sample resource route with sub-resources:
37 + #source code edit
38 - # resources :products do
38 + get 'sources/direct_edit/:pid', to: 'sources#direct_edit', as: 'direct_edit'
39 - # resources :comments, :sales
39 + get 'sources/direct_edit_submission/:sid', to: 'sources#direct_edit_submission', as: 'direct_edit_submission'
40 - # resource :seller
40 + get 'sources/get_latest_submission_status/:uid/:pid', to: 'sources#get_latest_submission_status', as: 'get_latest_submission_status'
41 - # end
42
41
43 - # Sample resource route with more complex sub-resources
44 - # resources :products do
45 - # resources :comments
46 - # resources :sales do
47 - # get 'recent', :on => :collection
48 - # end
49 - # end
50 -
51 - # Sample resource route within a namespace:
52 - # namespace :admin do
53 - # # Directs /admin/products/* to Admin::ProductsController
54 - # # (app/controllers/admin/products_controller.rb)
55 - # resources :products
56 - # end
57 -
58 - # You can have the root of your site routed with "root"
59 - # just remember to delete public/index.html.
60 - # root :to => 'welcome#index'
61 -
62 - root :to => 'main#login'
63
42
64 match 'tasks/view/:file.:ext' => 'tasks#view'
43 match 'tasks/view/:file.:ext' => 'tasks#view'
65 match 'tasks/download/:id/:file.:ext' => 'tasks#download'
44 match 'tasks/download/:id/:file.:ext' => 'tasks#download'
45 + match 'heartbeat/:id/edit' => 'heartbeat#edit'
66
46
67 - match 'heartbeat/:id/edit' => 'heartbeat#edit'
47 + #main
48 + get "main/list"
49 + get 'main/submission(/:id)', to: 'main#submission', as: 'main_submission'
50 +
51 + #report
52 + get 'report/problem_hof(/:id)', to: 'report#problem_hof', as: 'report_problem_hof'
53 + get "report/login"
54 +
55 + #grader
56 + get 'graders/list', to: 'graders#list', as: 'grader_list'
68
57
69 # See how all your routes lay out with "rake routes"
58 # See how all your routes lay out with "rake routes"
70
59
@@ -15,12 +15,12
15
15
16 create_table "announcements", :force => true do |t|
16 create_table "announcements", :force => true do |t|
17 t.string "author"
17 t.string "author"
18 - t.text "body", :limit => 16777215
18 + t.text "body"
19 t.boolean "published"
19 t.boolean "published"
20 - t.datetime "created_at", :null => false
20 + t.datetime "created_at", :null => false
21 - t.datetime "updated_at", :null => false
21 + t.datetime "updated_at", :null => false
22 - t.boolean "frontpage", :default => false
22 + t.boolean "frontpage", :default => false
23 - t.boolean "contest_only", :default => false
23 + t.boolean "contest_only", :default => false
24 t.string "title"
24 t.string "title"
25 t.string "notes"
25 t.string "notes"
26 end
26 end
@@ -50,19 +50,19
50 end
50 end
51
51
52 create_table "descriptions", :force => true do |t|
52 create_table "descriptions", :force => true do |t|
53 - t.text "body", :limit => 16777215
53 + t.text "body"
54 t.boolean "markdowned"
54 t.boolean "markdowned"
55 - t.datetime "created_at", :null => false
55 + t.datetime "created_at", :null => false
56 - t.datetime "updated_at", :null => false
56 + t.datetime "updated_at", :null => false
57 end
57 end
58
58
59 create_table "grader_configurations", :force => true do |t|
59 create_table "grader_configurations", :force => true do |t|
60 t.string "key"
60 t.string "key"
61 t.string "value_type"
61 t.string "value_type"
62 t.string "value"
62 t.string "value"
63 - t.datetime "created_at", :null => false
63 + t.datetime "created_at", :null => false
64 - t.datetime "updated_at", :null => false
64 + t.datetime "updated_at", :null => false
65 - t.text "description", :limit => 16777215
65 + t.text "description"
66 end
66 end
67
67
68 create_table "grader_processes", :force => true do |t|
68 create_table "grader_processes", :force => true do |t|
@@ -107,10 +107,10
107 t.integer "sender_id"
107 t.integer "sender_id"
108 t.integer "receiver_id"
108 t.integer "receiver_id"
109 t.integer "replying_message_id"
109 t.integer "replying_message_id"
110 - t.text "body", :limit => 16777215
110 + t.text "body"
111 t.boolean "replied"
111 t.boolean "replied"
112 - t.datetime "created_at", :null => false
112 + t.datetime "created_at", :null => false
113 - t.datetime "updated_at", :null => false
113 + t.datetime "updated_at", :null => false
114 end
114 end
115
115
116 create_table "problems", :force => true do |t|
116 create_table "problems", :force => true do |t|
@@ -152,7 +152,7
152
152
153 create_table "sessions", :force => true do |t|
153 create_table "sessions", :force => true do |t|
154 t.string "session_id"
154 t.string "session_id"
155 - t.text "data", :limit => 16777215
155 + t.text "data"
156 t.datetime "updated_at"
156 t.datetime "updated_at"
157 end
157 end
158
158
@@ -180,14 +180,14
180 t.integer "user_id"
180 t.integer "user_id"
181 t.integer "problem_id"
181 t.integer "problem_id"
182 t.integer "language_id"
182 t.integer "language_id"
183 - t.text "source", :limit => 16777215
183 + t.text "source"
184 t.binary "binary"
184 t.binary "binary"
185 t.datetime "submitted_at"
185 t.datetime "submitted_at"
186 t.datetime "compiled_at"
186 t.datetime "compiled_at"
187 - t.text "compiler_message", :limit => 16777215
187 + t.text "compiler_message"
188 t.datetime "graded_at"
188 t.datetime "graded_at"
189 t.integer "points"
189 t.integer "points"
190 - t.text "grader_comment", :limit => 16777215
190 + t.text "grader_comment"
191 t.integer "number"
191 t.integer "number"
192 t.string "source_filename"
192 t.string "source_filename"
193 t.float "max_runtime"
193 t.float "max_runtime"
@@ -208,10 +208,10
208
208
209 create_table "test_pairs", :force => true do |t|
209 create_table "test_pairs", :force => true do |t|
210 t.integer "problem_id"
210 t.integer "problem_id"
211 - t.text "input", :limit => 2147483647
211 + t.text "input", :limit => 16777215
212 - t.text "solution", :limit => 2147483647
212 + t.text "solution", :limit => 16777215
213 - t.datetime "created_at", :null => false
213 + t.datetime "created_at", :null => false
214 - t.datetime "updated_at", :null => false
214 + t.datetime "updated_at", :null => false
215 end
215 end
216
216
217 create_table "test_requests", :force => true do |t|
217 create_table "test_requests", :force => true do |t|
@@ -222,13 +222,13
222 t.string "output_file_name"
222 t.string "output_file_name"
223 t.string "running_stat"
223 t.string "running_stat"
224 t.integer "status"
224 t.integer "status"
225 - t.datetime "updated_at", :null => false
225 + t.datetime "updated_at", :null => false
226 t.datetime "submitted_at"
226 t.datetime "submitted_at"
227 t.datetime "compiled_at"
227 t.datetime "compiled_at"
228 - t.text "compiler_message", :limit => 16777215
228 + t.text "compiler_message"
229 t.datetime "graded_at"
229 t.datetime "graded_at"
230 t.string "grader_comment"
230 t.string "grader_comment"
231 - t.datetime "created_at", :null => false
231 + t.datetime "created_at", :null => false
232 t.float "running_time"
232 t.float "running_time"
233 t.string "exit_status"
233 t.string "exit_status"
234 t.integer "memory_usage"
234 t.integer "memory_usage"
@@ -256,7 +256,6
256 t.boolean "activated", :default => false
256 t.boolean "activated", :default => false
257 t.datetime "created_at"
257 t.datetime "created_at"
258 t.datetime "updated_at"
258 t.datetime "updated_at"
259 - t.string "section"
260 t.boolean "enabled", :default => true
259 t.boolean "enabled", :default => true
261 t.string "remark"
260 t.string "remark"
262 t.string "last_ip"
261 t.string "last_ip"
deleted file
deleted file
deleted file
deleted file
deleted file
deleted file
deleted file
deleted file
deleted file
deleted file
deleted file
You need to be logged in to leave comments. Login now