Merge branch 'dev_aliyun' of http://bdgit.educoder.net/Hjqreturn/educoder into dev_aliyun
commit
cfc6dbbae6
@ -0,0 +1,2 @@
|
||||
// Place all the behaviors and hooks related to the matching controller here.
|
||||
// All this logic will automatically be available in application.js.
|
@ -0,0 +1,2 @@
|
||||
// Place all the behaviors and hooks related to the matching controller here.
|
||||
// All this logic will automatically be available in application.js.
|
@ -0,0 +1,3 @@
|
||||
// Place all the styles related to the HackUserLastestCodes controller here.
|
||||
// They will automatically be included in application.css.
|
||||
// You can use Sass (SCSS) here: http://sass-lang.com/
|
@ -0,0 +1,3 @@
|
||||
// Place all the styles related to the hacks controller here.
|
||||
// They will automatically be included in application.css.
|
||||
// You can use Sass (SCSS) here: http://sass-lang.com/
|
@ -0,0 +1,180 @@
|
||||
class HacksController < ApplicationController
|
||||
before_action :require_login, except: [:index]
|
||||
before_action :require_teacher_identity, only: [:create, :edit, :update]
|
||||
before_action :require_auth_identity, only: [:update, :edit, :publish]
|
||||
before_action :find_hack, only: [:edit, :update, :publish, :start]
|
||||
|
||||
# 开启编程,如果第一次开启,创建一条记录,如果已经开启过的话,直接返回标识即可
|
||||
def start
|
||||
# 未发布的编程题,只能作者、或管理员访问
|
||||
start_hack_auth
|
||||
user_hack = @hack.hack_user_lastest_codes.mine(current_user.id)
|
||||
identifier =
|
||||
if user_hack.present?
|
||||
user_hack.identifier
|
||||
else
|
||||
user_identifier = generate_identifier HackUserLastestCode, 12
|
||||
user_code = {user_id: current_user.id, code: @hack.code,
|
||||
identifier: user_identifier, language: @hack.language}
|
||||
@hack.hack_user_lastest_codes.create!(user_code)
|
||||
user_identifier
|
||||
end
|
||||
render_ok(data: {identifier: identifier})
|
||||
end
|
||||
|
||||
# 首页
|
||||
def index
|
||||
# 筛选过滤与排序
|
||||
params_filter_or_order
|
||||
# 我解决的编程题数
|
||||
user_codes = HackUserLastestCode.mine(current_user).passed.joins(:hack)
|
||||
@simple_count = user_codes.where(hacks: {difficult: 1}).count
|
||||
@medium_count = user_codes.where(hacks: {difficult: 2}).count
|
||||
@diff_count = user_codes.where(hacks: {difficult: 3}).count
|
||||
@pass_count = @simple_count + @medium_count + @diff_count
|
||||
|
||||
@hacks_count = @hacks.count("hacks.id")
|
||||
@hacks = paginate @hacks
|
||||
end
|
||||
|
||||
def create
|
||||
begin
|
||||
logger.info("##########{hack_params}")
|
||||
hack = Hack.new(hack_params)
|
||||
ActiveRecord::Base.transaction do
|
||||
hack.user_id = current_user.id
|
||||
hack.identifier = generate_identifier Hack, 8
|
||||
hack.save!
|
||||
# 创建测试集与代码
|
||||
hack.hack_sets.create!(hack_sets_params)
|
||||
hack.hack_codes.create!(hack_code_params)
|
||||
end
|
||||
render_ok({identifier: hack.identifier})
|
||||
rescue Exception => e
|
||||
logger.error("########create_hack_error: #{e.message}")
|
||||
render_error("创建失败")
|
||||
end
|
||||
end
|
||||
|
||||
def update
|
||||
begin
|
||||
ActiveRecord::Base.transaction do
|
||||
@hack.update_attributes!(hack_params)
|
||||
set_ids = @hack.hack_sets.pluck(:id)
|
||||
# 更新
|
||||
param_update_sets params[:update_hack_sets], set_ids
|
||||
# 新建
|
||||
@hack.hack_sets.create!(hack_sets_params)
|
||||
# 更新代码
|
||||
@hack.hack_codes.create!(hack_code_params)
|
||||
end
|
||||
render_ok
|
||||
rescue Exception => e
|
||||
logger.error("####update_hack_error: #{e.message}")
|
||||
render_error("更新失败")
|
||||
end
|
||||
end
|
||||
|
||||
# 发布功能
|
||||
def publish
|
||||
@hack.update_attribute(:status, 1)
|
||||
render_ok
|
||||
end
|
||||
|
||||
# 发布列表
|
||||
def unpulished_list
|
||||
limit = params[:limit] || 16
|
||||
page = params[:page] || 1
|
||||
hacks = Hack.where(user_id: current_user.id, status: 0)
|
||||
@hacks_count = hacks.count
|
||||
@hacks = hacks.includes(:hack_sets).page(page).per(limit)
|
||||
end
|
||||
|
||||
def edit;end
|
||||
|
||||
private
|
||||
# 实名认证老师,管理员与运营人员权限
|
||||
def require_teacher_identity
|
||||
unless current_user.certification_teacher? || admin_or_business?
|
||||
tip_exception(403, "..")
|
||||
end
|
||||
end
|
||||
|
||||
# 只有自己,或者管理员才能更新
|
||||
def require_auth_identity
|
||||
unless @hack.user_id == current_user.id || admin_or_business?
|
||||
tip_exception(403, "..")
|
||||
end
|
||||
end
|
||||
|
||||
def find_hack
|
||||
@hack = Hack.find_by_identifier(params[:identifier])
|
||||
end
|
||||
|
||||
def hack_params
|
||||
params.require(:hack).permit(:name, :description, :difficult, :category, :open_or_not, :time_limit, :score)
|
||||
end
|
||||
|
||||
def hack_sets_params
|
||||
params.permit(hack_sets: [:input, :output, :position])[:hack_sets]
|
||||
end
|
||||
|
||||
def hack_code_params
|
||||
params.require(:hack_codes).permit(:code, :language)
|
||||
end
|
||||
|
||||
def publish_params
|
||||
params.require(:hack).permit(:difficult, :category, :open_or_not, :time_limit, :score)
|
||||
end
|
||||
|
||||
def param_update_sets sets, all_sets_id
|
||||
delete_set_ids = all_sets_id - sets.map{|set|set[:id]}
|
||||
@hack.hack_sets.where(id: delete_set_ids).destroy_all
|
||||
sets.each do |set|
|
||||
if all_sets_id.include?(set[:id])
|
||||
update_attrs = {input: set[:input], output: set[:output], position: set[:position]}
|
||||
@hack.hack_sets.find_by!(id: set[:id]).update_attributes(update_attrs)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
def params_filter_or_order
|
||||
# 如果有来源,就不管发布公开私有
|
||||
select_sql = "hacks.*, if(hacks.hack_user_lastest_codes_count=0, 0, hacks.pass_num/hacks.hack_user_lastest_codes_count) passed_rate"
|
||||
if params[:come_from]
|
||||
hacks = Hack.select(select_sql).mine(current_user.id)
|
||||
else
|
||||
hacks = Hack.select(select_sql).published.opening
|
||||
end
|
||||
# 搜索
|
||||
if params[:search]
|
||||
hacks = hacks.where("name like ?", "%#{params[:search]}%")
|
||||
end
|
||||
# 难度
|
||||
if params[:difficult]
|
||||
hacks = hacks.where(difficult: params[:difficult])
|
||||
end
|
||||
# 状态
|
||||
if params[:status]
|
||||
user_hacks = HackUserLastestCode.where(user_id: current_user.id)
|
||||
if params[:status].to_i == -1
|
||||
if user_hacks.present?
|
||||
hacks = hacks.where.not(id: user_hacks.pluck(:hack_id))
|
||||
end
|
||||
else
|
||||
hacks = hacks.joins(:hack_user_lastest_code).where(hack_user_lastest_code: {status: params[:status]})
|
||||
end
|
||||
end
|
||||
# 排序
|
||||
sort_by = params[:sort_by] || "hack_user_lastest_codes_count"
|
||||
sort_direction = params[:sort_direction] || "desc"
|
||||
@hacks = hacks.order("#{sort_by} #{sort_direction}")
|
||||
end
|
||||
|
||||
def start_hack_auth
|
||||
return true if @hack == 1
|
||||
require_auth_identity
|
||||
end
|
||||
|
||||
|
||||
end
|
@ -0,0 +1,2 @@
|
||||
module HackUserLastestCodesHelper
|
||||
end
|
@ -0,0 +1,2 @@
|
||||
module HacksHelper
|
||||
end
|
@ -0,0 +1,3 @@
|
||||
class HackCode < ApplicationRecord
|
||||
# 编程题代码相关
|
||||
end
|
@ -0,0 +1,4 @@
|
||||
class HackSet < ApplicationRecord
|
||||
# 编程题测试集
|
||||
belongs_to :hack
|
||||
end
|
@ -0,0 +1,4 @@
|
||||
class HackUserCode < ApplicationRecord
|
||||
# 用户编程题的信息
|
||||
belongs_to :hack
|
||||
end
|
@ -0,0 +1,4 @@
|
||||
class HackUserDebug < ApplicationRecord
|
||||
belongs_to :hack
|
||||
belongs_to :hack_user_lastest_code
|
||||
end
|
@ -0,0 +1,12 @@
|
||||
json.hack do
|
||||
json.(@hack, :difficult, :time_limit, :description, :score, :identifier)
|
||||
json.language @hack.language
|
||||
json.username @hack.user.real_name
|
||||
json.code @my_hack.code
|
||||
json.pass_count @hack.pass_num
|
||||
json.submit_count @hack.submit_num
|
||||
end
|
||||
|
||||
json.test_case do
|
||||
json.input @hack.input_test_case
|
||||
end
|
@ -0,0 +1,13 @@
|
||||
# 编程内容
|
||||
json.(@hack, :name, :description, :language, :code)
|
||||
|
||||
# 代码
|
||||
json.language @hack.language
|
||||
json.code @hack.code
|
||||
|
||||
# 测试集
|
||||
json.hack_sets do
|
||||
json.array! @hack.hack_sets do |set|
|
||||
json.(set, :id, :input, :output, :position)
|
||||
end
|
||||
end
|
@ -0,0 +1,13 @@
|
||||
json.top_data do
|
||||
json.passed_count @pass_count
|
||||
json.simple_count @simple_count
|
||||
json.medium_count @medium_count
|
||||
json.diff_count @diff_count
|
||||
end
|
||||
|
||||
json.hacks_count @hacks_count
|
||||
json.hacks_list do
|
||||
json.array! @hacks do |hack|
|
||||
json.(hack,:identifier, :name , :hack_user_lastest_codes_count, :difficult, :passed_rate, :category)
|
||||
end
|
||||
end
|
@ -0,0 +1,5 @@
|
||||
json.hacks_count @hacks_count
|
||||
json.hacks @hacks do |hack|
|
||||
json.(hack, :name, :difficult, :updated_at)
|
||||
json.sets_count hack.hack_sets.count
|
||||
end
|
@ -0,0 +1,20 @@
|
||||
class CreateHacks < ActiveRecord::Migration[5.2]
|
||||
def change
|
||||
create_table :hacks do |t|
|
||||
t.string :name
|
||||
t.integer :difficult
|
||||
t.integer :category
|
||||
t.integer :status, default: 0
|
||||
t.boolean :open_or_not, default: true
|
||||
t.integer :time_limit
|
||||
t.integer :memory_limit
|
||||
t.string :identifier
|
||||
t.references :user
|
||||
t.text :description
|
||||
|
||||
t.timestamps
|
||||
end
|
||||
|
||||
add_index :hacks, :identifier, unique: true
|
||||
end
|
||||
end
|
@ -0,0 +1,11 @@
|
||||
class CreateHackCodes < ActiveRecord::Migration[5.2]
|
||||
def change
|
||||
create_table :hack_codes do |t|
|
||||
t.references :hack
|
||||
t.text :code
|
||||
t.string :language
|
||||
|
||||
t.timestamps
|
||||
end
|
||||
end
|
||||
end
|
@ -0,0 +1,13 @@
|
||||
class CreateHackSets < ActiveRecord::Migration[5.2]
|
||||
def change
|
||||
create_table :hack_sets do |t|
|
||||
t.references :hack
|
||||
t.text :input
|
||||
t.text :output
|
||||
t.integer :position
|
||||
|
||||
t.timestamps
|
||||
end
|
||||
add_index :hack_sets, [:hack_id, :position], unique: true
|
||||
end
|
||||
end
|
@ -0,0 +1,18 @@
|
||||
class CreateHackUserCodes < ActiveRecord::Migration[5.2]
|
||||
def change
|
||||
create_table :hack_user_codes do |t|
|
||||
t.references :user
|
||||
t.references :hack
|
||||
t.text :code
|
||||
t.text :output
|
||||
t.text :error_msg
|
||||
t.integer :error_line
|
||||
t.integer :position
|
||||
t.integer :status, default: 0
|
||||
t.integer :query_index
|
||||
t.timestamps
|
||||
end
|
||||
|
||||
add_index :hack_user_codes, [:user_id, :hack_id, :query_index], unique: true
|
||||
end
|
||||
end
|
@ -0,0 +1,12 @@
|
||||
class CreateHackUserLastestCodes < ActiveRecord::Migration[5.2]
|
||||
def change
|
||||
create_table :hack_user_lastest_codes do |t|
|
||||
t.references :user
|
||||
t.references :hack
|
||||
t.text :code
|
||||
|
||||
t.timestamps
|
||||
end
|
||||
add_index :hack_user_lastest_codes, [:user_id, :hack_id], unique: true
|
||||
end
|
||||
end
|
@ -0,0 +1,14 @@
|
||||
class CreateHackUserDebugs < ActiveRecord::Migration[5.2]
|
||||
def change
|
||||
create_table :hack_user_debugs do |t|
|
||||
t.references :user
|
||||
t.references :hack
|
||||
t.text :output
|
||||
t.text :input
|
||||
t.text :error_msg
|
||||
t.integer :error_line
|
||||
|
||||
t.timestamps
|
||||
end
|
||||
end
|
||||
end
|
@ -0,0 +1,7 @@
|
||||
class AddDefualtForHacks < ActiveRecord::Migration[5.2]
|
||||
def change
|
||||
change_column :hacks, :status, :integer, :default => 0
|
||||
change_column :hacks, :open_or_not, :boolean, :default => true
|
||||
change_column :hack_user_codes, :status, :integer, :default => 0
|
||||
end
|
||||
end
|
@ -0,0 +1,5 @@
|
||||
class AddScoreForHacks < ActiveRecord::Migration[5.2]
|
||||
def change
|
||||
add_column :hacks, :score, :integer
|
||||
end
|
||||
end
|
@ -0,0 +1,27 @@
|
||||
class AddStatusEndTimeForHackUserLastestCode < ActiveRecord::Migration[5.2]
|
||||
def change
|
||||
add_column :hack_user_lastest_codes, :passed, :boolean, :default => false
|
||||
add_column :hack_user_lastest_codes, :pass_time, :timestamp
|
||||
add_column :hack_user_lastest_codes, :identifier, :string
|
||||
add_column :hack_user_lastest_codes, :language, :string
|
||||
add_column :hack_user_debugs, :hack_user_lastest_code_id, :integer
|
||||
add_column :hacks, :hack_user_lastest_codes_count, :integer, :default => 0
|
||||
add_column :hacks, :pass_num, :integer, :default => 0
|
||||
add_column :hacks, :submit_num, :integer, :default => 0
|
||||
add_column :hack_user_codes, :input, :text
|
||||
add_index :hack_user_lastest_codes, :user_id, name: "user_index"
|
||||
add_index :hack_user_lastest_codes, :hack_id, name: "hack_index"
|
||||
add_index :hack_user_lastest_codes, :identifier, unique: true
|
||||
add_index :hack_user_debugs, :hack_user_lastest_code_id, unique: true
|
||||
add_column :hack_user_lastest_codes, :submit_status, :integer, :default => 0
|
||||
add_column :hack_user_lastest_codes, :status, :integer
|
||||
add_column :hack_user_lastest_codes, :passed_time, :timestamp
|
||||
add_column :hack_user_debugs, :status, :integer
|
||||
|
||||
add_column :hack_user_codes, :execute_time, :integer
|
||||
add_column :hack_user_codes, :execute_memory, :integer
|
||||
add_column :hack_user_debugs, :execute_time, :integer
|
||||
add_column :hack_user_debugs, :execute_memory, :integer
|
||||
|
||||
end
|
||||
end
|
@ -0,0 +1,7 @@
|
||||
class AddHackUserLastestCodeIdForHackUserCode < ActiveRecord::Migration[5.2]
|
||||
def change
|
||||
add_column :hack_user_codes, :hack_user_lastest_code_id, :integer
|
||||
add_index :hack_user_codes, :hack_user_lastest_code_id
|
||||
|
||||
end
|
||||
end
|
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
@ -0,0 +1,5 @@
|
||||
require 'rails_helper'
|
||||
|
||||
RSpec.describe HackUserLastestCodesController, type: :controller do
|
||||
|
||||
end
|
@ -0,0 +1,5 @@
|
||||
require 'rails_helper'
|
||||
|
||||
RSpec.describe HacksController, type: :controller do
|
||||
|
||||
end
|
@ -0,0 +1,15 @@
|
||||
require 'rails_helper'
|
||||
|
||||
# Specs in this file have access to a helper object that includes
|
||||
# the HackUserLastestCodesHelper. For example:
|
||||
#
|
||||
# describe HackUserLastestCodesHelper do
|
||||
# describe "string concat" do
|
||||
# it "concats two strings with spaces" do
|
||||
# expect(helper.concat_strings("this","that")).to eq("this that")
|
||||
# end
|
||||
# end
|
||||
# end
|
||||
RSpec.describe HackUserLastestCodesHelper, type: :helper do
|
||||
pending "add some examples to (or delete) #{__FILE__}"
|
||||
end
|
@ -0,0 +1,15 @@
|
||||
require 'rails_helper'
|
||||
|
||||
# Specs in this file have access to a helper object that includes
|
||||
# the HacksHelper. For example:
|
||||
#
|
||||
# describe HacksHelper do
|
||||
# describe "string concat" do
|
||||
# it "concats two strings with spaces" do
|
||||
# expect(helper.concat_strings("this","that")).to eq("this that")
|
||||
# end
|
||||
# end
|
||||
# end
|
||||
RSpec.describe HacksHelper, type: :helper do
|
||||
pending "add some examples to (or delete) #{__FILE__}"
|
||||
end
|
@ -0,0 +1,5 @@
|
||||
require 'rails_helper'
|
||||
|
||||
RSpec.describe HackCode, type: :model do
|
||||
pending "add some examples to (or delete) #{__FILE__}"
|
||||
end
|
@ -0,0 +1,5 @@
|
||||
require 'rails_helper'
|
||||
|
||||
RSpec.describe HackSet, type: :model do
|
||||
pending "add some examples to (or delete) #{__FILE__}"
|
||||
end
|
@ -0,0 +1,5 @@
|
||||
require 'rails_helper'
|
||||
|
||||
RSpec.describe Hack, type: :model do
|
||||
pending "add some examples to (or delete) #{__FILE__}"
|
||||
end
|
@ -0,0 +1,5 @@
|
||||
require 'rails_helper'
|
||||
|
||||
RSpec.describe HackUserCode, type: :model do
|
||||
pending "add some examples to (or delete) #{__FILE__}"
|
||||
end
|
@ -0,0 +1,5 @@
|
||||
require 'rails_helper'
|
||||
|
||||
RSpec.describe HackUserDebug, type: :model do
|
||||
pending "add some examples to (or delete) #{__FILE__}"
|
||||
end
|
@ -0,0 +1,5 @@
|
||||
require 'rails_helper'
|
||||
|
||||
RSpec.describe HackUserLastestCode, type: :model do
|
||||
pending "add some examples to (or delete) #{__FILE__}"
|
||||
end
|
Loading…
Reference in new issue