Merge branch 'dev_aliyun' of https://bdgit.educoder.net/Hjqreturn/educoder into dev_aliyun

dev_admin
杨树林 6 years ago
commit ccbc6aa7b3

@ -160,7 +160,7 @@ class AccountsController < ApplicationController
# 发送验证码 # 发送验证码
# params[:login] 手机号或者邮箱号 # params[:login] 手机号或者邮箱号
# params[:type]为事件通知类型 1用户注册注册 2忘记密码 3: 绑定手机 4: 绑定邮箱 # 如果有新的继续后面加 # params[:type]为事件通知类型 1用户注册注册 2忘记密码 3: 绑定手机 4: 绑定邮箱, 5: 验收手机号有效 # 如果有新的继续后面加
# 发送验证码send_type 1注册手机验证码 2找回密码手机验证码 3找回密码邮箱验证码 4绑定手机 5绑定邮箱 # 发送验证码send_type 1注册手机验证码 2找回密码手机验证码 3找回密码邮箱验证码 4绑定手机 5绑定邮箱
# 6手机验证码登录 7邮箱验证码登录 8邮箱注册验证码 9: 验收手机号有效 # 6手机验证码登录 7邮箱验证码登录 8邮箱注册验证码 9: 验收手机号有效
def get_verification_code def get_verification_code
@ -200,7 +200,7 @@ class AccountsController < ApplicationController
session[:user_id] = nil session[:user_id] = nil
end end
# type 事件类型 1用户注册 2忘记密码 3: 绑定手机 4: 绑定邮箱 # 如果有新的继续后面加 # type 事件类型 1用户注册 2忘记密码 3: 绑定手机 4: 绑定邮箱, 5: 验证手机号是否有效 # 如果有新的继续后面加
# login_type 1手机类型 2邮箱类型 # login_type 1手机类型 2邮箱类型
def verify_type login_type, type def verify_type login_type, type
case type case type
@ -212,6 +212,8 @@ class AccountsController < ApplicationController
login_type == 1 ? 4 : tip_exception('请填写正确的手机号') login_type == 1 ? 4 : tip_exception('请填写正确的手机号')
when 4 when 4
login_type == 1 ? tip_exception('请填写正确的邮箱') : 5 login_type == 1 ? tip_exception('请填写正确的邮箱') : 5
when 5
login_type == 1 ? 9 : tip_exception('请填写正确的手机号')
end end
end end

@ -64,10 +64,10 @@ class ApplicationController < ActionController::Base
# 发送及记录激活码 # 发送及记录激活码
# 发送验证码type 1注册手机验证码 2找回密码手机验证码 3找回密码邮箱验证码 4绑定手机 5绑定邮箱 # 发送验证码type 1注册手机验证码 2找回密码手机验证码 3找回密码邮箱验证码 4绑定手机 5绑定邮箱
# 6手机验证码登录 7邮箱验证码登录 8邮箱注册验证码 # 6手机验证码登录 7邮箱验证码登录 8邮箱注册验证码 9验证手机号有效
def check_verification_code(code, send_type, value) def check_verification_code(code, send_type, value)
case send_type case send_type
when 1, 2, 4 when 1, 2, 4, 9
# 手机类型的发送 # 手机类型的发送
sigle_para = {phone: value} sigle_para = {phone: value}
status = Educoder::Sms.send(mobile: value, code: code) status = Educoder::Sms.send(mobile: value, code: code)
@ -241,6 +241,9 @@ class ApplicationController < ActionController::Base
User.current = User.find 57703 User.current = User.find 57703
end end
# 测试版前端需求
if request.host == "47.96.87.25"
if params[:debug] == 'teacher' #todo 为了测试,记得讲debug删除 if params[:debug] == 'teacher' #todo 为了测试,记得讲debug删除
User.current = User.find 81403 User.current = User.find 81403
elsif params[:debug] == 'student' elsif params[:debug] == 'student'
@ -248,7 +251,7 @@ class ApplicationController < ActionController::Base
elsif params[:debug] == 'admin' elsif params[:debug] == 'admin'
User.current = User.find 1 User.current = User.find 1
end end
end
# User.current = User.find 81403 # User.current = User.find 81403
end end

@ -1,7 +1,7 @@
class DiscussesController < ApplicationController class DiscussesController < ApplicationController
LIMIT = 10 LIMIT = 10
before_action :find_container, only: [:index, :hidden] before_action :find_container, only: [:index, :hidden]
before_action :find_discuss, except: [:create, :index, :new_message, :reward_code] before_action :find_discuss, except: [:create, :index, :new_message, :reward_code, :forum_discusses]
def index def index
page = params[:page].to_i page = params[:page].to_i
@ -28,6 +28,48 @@ class DiscussesController < ApplicationController
@current_user = current_user @current_user = current_user
end end
def forum_discusses
page = params[:page] || 1
limit = params[:limit] || 15
offset = (page.to_i-1) * limit
search = params[:search]
tag = params[:tag_repertoire_id]
sql, sql1, sql2 = '', '', ''
sql1 =
unless search.blank?
"and d.content like '%#{search}%'"
end
sql2 =
if tag
shixun_ids = ShixunTagRepertoire.where(:tag_repertoire_id => tag).pluck(:shixun_id)
"and d.dis_id in(#{shixun_ids.join(",")})"
end
sql = "select d.id from discusses d join shixuns s on d.dis_id = s.id where s.status = 2 and s.hidden = false and d.root_id is null
and d.hidden = false #{sql1} #{sql2} order by d.created_at desc"
memo_ids = Discuss.find_by_sql(sql).pluck(:id)
@memo_count = memo_ids.size
memo_ids = memo_ids[offset, limit]
order_ids = memo_ids.size > 0 ? memo_ids.join(',') : -1
@memos = Discuss.where(id: memo_ids).order("field(id,#{order_ids})").includes(:praise_treads, dis: :tag_repertoires, user: :user_extension)
# @memos = memos.includes(:praise_treads, user: :user_extension).page(page).per(limit)
# 实训标签使用最多的9个
# @hot_tags = TagRepertoire.find_by_sql("select distinct(a.name), a.id from
# (select tr.id, tr.name, count(d.dis_id) cnt
# from tag_repertoires tr join (shixun_tag_repertoires str
# left join (shixuns s join discusses d on d.dis_id = s.id)
# on s.id = str.shixun_id) on tr.id = str.tag_repertoire_id
# group by d.dis_id order by cnt desc) a limit 9").map{|ht| ht.attributes.dup}
tag_id = ShixunTagRepertoire.joins(:shixun).order("myshixuns_count desc").pluck(:tag_repertoire_id).uniq.first(9)
@hot_tags = TagRepertoire.select([:id, :name]).where(id: tag_id).order("FIELD(id, #{tag_id.join(",")})").map{|ht| ht.attributes.dup} if tag_id
@memos = DiscussesService.new.memo_list @memos
@hot_memos = Memo.field_for_recommend.posts.hot.includes(:tag_repertoires).limit(4)
@recommend_shixuns = DiscussesService.new.recommends
end
def new_message def new_message
onclick_time = Myshixun.find(params[:myshixun_id]).try(:onclick_time) onclick_time = Myshixun.find(params[:myshixun_id]).try(:onclick_time)
ids = Discuss.where(user_id: User.current.id, dis_id: params[:container_id], dis_type: params[:container_type]). ids = Discuss.where(user_id: User.current.id, dis_id: params[:container_id], dis_type: params[:container_type]).

@ -336,7 +336,7 @@ class HomeworkCommonsController < ApplicationController
@messages = @messages.parent_comment @messages = @messages.parent_comment
end end
@messages = @messages.page(@page).per(@limit).order("created_on desc") @messages = @messages.includes(:praise_treads).page(@page).per(@limit).order("created_on desc")
end end
def reference_answer def reference_answer

@ -1,5 +1,8 @@
class MemosController < ApplicationController class MemosController < ApplicationController
before_action :set_memo, only: [:show, :edit, :update, :destroy] before_action :set_memo, only: [:show, :edit, :update, :destroy]
before_action :validate_memo_params, only: [:create, :update]
before_action :owner_or_admin, only: [:edit, :update, :destroy]
before_action :is_admin, only: []
include ApplicationHelper include ApplicationHelper
# GET /memos # GET /memos
@ -8,26 +11,20 @@ class MemosController < ApplicationController
@user = current_user @user = current_user
@memos = Memo.all @memos = Memo.all
s_order = (params[:order] == "replies_count" ? "all_replies_count" : params[:order]) || "updated_at" s_order = (params[:order] == "replies_count" ? "all_replies_count" : params[:order]) || "updated_at"
#@tidding_count = unviewed_tiddings(current_user) if current_user.present? # @tidding_count = unviewed_tiddings(current_user) if current_user.present?
page = params[:page].to_i page = params[:page] || 1
limit = params[:limit] || 15
search = params[:search] search = params[:search]
offset = page * 15
forum_id = params[:forum] forum_id = params[:forum]
user_id = params[:user_id]
if user_id == -1
user_id = current_user.try(:id)
end
tag_repertoire_id = params[:tag_repertoire_id] tag_repertoire_id = params[:tag_repertoire_id]
sql = sql =
if forum_id if forum_id
search ? "forum_id = #{forum_id} and root_id is null and subject like '%#{search}%'" : !search.blank? ? "forum_id = #{forum_id} and root_id is null and subject like '%#{search}%'" :
"forum_id = #{forum_id} and root_id is null" "forum_id = #{forum_id} and root_id is null"
elsif search elsif !search.blank?
user_id ? "author_id = #{user_id.to_i} and forum_id in(3, 5) and root_id is null and subject like '%#{search}%'" :
"forum_id in(3, 5) and root_id is null and subject like '%#{search}%'" "forum_id in(3, 5) and root_id is null and subject like '%#{search}%'"
else else
user_id ? "author_id = #{user_id.to_i} and forum_id in(3, 5) and root_id is null" :
"forum_id in(3, 5) and root_id is null" "forum_id in(3, 5) and root_id is null"
end end
@ -41,27 +38,27 @@ class MemosController < ApplicationController
sql += " and all_replies_count != 0" sql += " and all_replies_count != 0"
end end
memos = Memo.field_for_list.includes(:praise_tread, :author).where("#{sql}") memos = Memo.field_for_list.where("#{sql}")
@memos_count = memos.length @memos_count = memos.length
@memos = memos.order("sticky = 1 desc, #{Memo.table_name}.#{s_order} desc").offset(offset).limit(15) @memos = memos.order("sticky = 1 desc, #{Memo.table_name}.#{s_order} desc").page(page).per(limit)
@my_memos_count = Memo.user_posts(current_user.try(:id)).count @memos = @memos.includes(:praise_treads, :tag_repertoires, author: :user_extension)
# @my_memos_count = Memo.user_posts(current_user.try(:id)).count
@tags_info = MemoTagRepertoire.find_by_sql("SELECT tag_repertoire_id, tr.name, count(*) cnt @tags_info = MemoTagRepertoire.find_by_sql("SELECT tag_repertoire_id, tr.name, count(*) cnt
FROM memo_tag_repertoires mtr join tag_repertoires tr on FROM memo_tag_repertoires mtr join tag_repertoires tr on
tr.id = mtr.tag_repertoire_id group by tag_repertoire_id order by cnt desc, tr.id = mtr.tag_repertoire_id group by tag_repertoire_id order by cnt desc,
tag_repertoire_id desc limit 9") tag_repertoire_id desc limit 9")
@hot_memos = Memo.field_for_recommend.posts.hot.limit(4) @hot_memos = Memo.field_for_recommend.posts.hot.includes(:tag_repertoires).limit(4)
@recommend_shixuns = DiscussesService.new.recommends
end end
# GET /memos/1
# GET /memos/1.json # GET /memos/1.json
def show def show
# tidding_count = unviewed_tiddings(current_user) if current_user # tidding_count = unviewed_tiddings(current_user) if current_user
@user = current_user @user = current_user
# TODO 附件最后再做
# attachments_list =
@memo.update_column(:viewed_count, @memo.viewed_count+1) @memo.update_column(:viewed_count, @memo.viewed_count+1)
@memos = @memo.reply_for_memo.includes(:praise_tread, :author).order("created_at desc").limit(10) @memos = @memo.reply_for_memo.includes(:praise_treads, author: :user_extension).order("created_at desc").limit(10)
@attachments = @memo.attachments
@recommend_shixuns = DiscussesService.new.recommends
end end
# GET /memos/new # GET /memos/new
@ -71,43 +68,44 @@ class MemosController < ApplicationController
# GET /memos/1/edit # GET /memos/1/edit
def edit def edit
@tag_list = TagRepertoire.field_for_list.order("name asc")
@memo_tags = @memo.tag_repertoires.field_for_list
@attachments = @memo.attachments
end end
# POST /memos
# POST /memos.json # POST /memos.json
def create def create
ActiveRecord::Base.transaction do ActiveRecord::Base.transaction do
begin begin
@memo = Memo.new(memo_params) @memo = Memo.new(memo_params)
@memo.author = current_user @memo.author = current_user
# TODO 保存附件
# @memo.save_attachments(params[:attachments]) if params[:attachments]
@memo.save! @memo.save!
Attachment.associate_container(params[:attachment_ids], @memo.id, @memo.class.name)
params[:tags].each do |tag| params[:tags].each do |tag|
MemoTagRepertoire.create(:memo_id => @memo.id, :tag_repertoire_id => tag) MemoTagRepertoire.create!(memo_id: @memo.id, tag_repertoire_id: tag)
end end
@status = 0 normal_status("帖子创建成功")
@message = "帖子创建成功!"
rescue Exception => e rescue Exception => e
@status = -1 tip_exception("帖子创建失败,原因:#{e}")
@message = "帖子创建失败,原因:#{e}"
raise ActiveRecord::Rollback raise ActiveRecord::Rollback
end end
end end
end end
# PATCH/PUT /memos/1
# PATCH/PUT /memos/1.json # PATCH/PUT /memos/1.json
def update def update
respond_to do |format| ActiveRecord::Base.transaction do
if @memo.update(memo_params) begin
format.html { redirect_to @memo, notice: 'Memo was successfully updated.' } @memo.update_attributes!(memo_params)
format.json { render :show, status: :ok, location: @memo } Attachment.associate_container(params[:attachment_ids], @memo.id, @memo.class.name)
else @memo.memo_tag_repertoires.destroy_all
format.html { render :edit } params[:tags].each do |tag|
format.json { render json: @memo.errors, status: :unprocessable_entity } MemoTagRepertoire.create!(memo_id: @memo.id, tag_repertoire_id: tag)
end
normal_status("帖子更新成功")
rescue Exception => e
tip_exception("帖子更新失败,原因:#{e}")
raise ActiveRecord::Rollback
end end
end end
end end
@ -116,10 +114,7 @@ class MemosController < ApplicationController
# DELETE /memos/1.json # DELETE /memos/1.json
def destroy def destroy
@memo.destroy @memo.destroy
respond_to do |format| normal_status("删除成功")
format.html { redirect_to memos_url, notice: 'Memo was successfully destroyed.' }
format.json { head :no_content }
end
end end
private private
@ -128,9 +123,24 @@ class MemosController < ApplicationController
@memo = Memo.find(params[:id]) @memo = Memo.find(params[:id])
end end
def owner_or_admin
tip_exception(403, "无权限操作") unless @memo.author == current_user || current_user.admin? || current_user.business?
end
def is_admin
tip_exception(403, "无权限操作") unless current_user.admin? || current_user.business?
end
# Never trust parameters from the scary internet, only allow the white list through. # Never trust parameters from the scary internet, only allow the white list through.
def memo_params def memo_params
params.fetch(:memo, {}) params.require(:memo).permit(:subject, :content, :forum_id)
end
def validate_memo_params
tip_exception("话题名称不能为空") if params[:subject].blank?
tip_exception("话题内容不能为空") if params[:content].blank?
tip_exception("话题类型不能为空") if params[:forum_id].blank?
tip_exception("技术标签不能为空") if params[:tags].blank?
end end
end end

@ -329,6 +329,23 @@ module ApplicationHelper
content content
end end
def strip_html(text, len=0, endss="...")
ss = ""
if !text.nil? && text.length>0
ss=text.gsub(/<\/?.*?>/, '').strip
ss = ss.gsub(/&nbsp;*/, '')
ss = ss.gsub(/\r\n/,'') #新增
ss = ss.gsub(/\n/,'') #新增
if len > 0 && ss.length > len
ss = ss[0, len] + endss
elsif len > 0 && ss.length <= len
ss = ss
#ss = truncate(ss, :length => len)
end
end
ss
end
def strip_export_title(content) def strip_export_title(content)
con_ = "" con_ = ""
if content.length > 0 if content.length > 0

@ -8,6 +8,7 @@ class Discuss < ApplicationRecord
has_many :praise_treads, as: :praise_tread_object, dependent: :destroy has_many :praise_treads, as: :praise_tread_object, dependent: :destroy
has_many :tidings, as: :container, dependent: :destroy has_many :tidings, as: :container, dependent: :destroy
has_one :praise_tread_cache, as: :object, dependent: :destroy has_one :praise_tread_cache, as: :object, dependent: :destroy
belongs_to :dis, polymorphic: true
belongs_to :challenge belongs_to :challenge
after_create :send_tiding after_create :send_tiding
@ -44,6 +45,10 @@ class Discuss < ApplicationRecord
Discuss.where(parent_id: self.id).includes(:user).reorder(created_at: :asc) Discuss.where(parent_id: self.id).includes(:user).reorder(created_at: :asc)
end end
def child_discuss_count
Discuss.where(root_id: id).count
end
private private
def send_tiding def send_tiding

@ -6,7 +6,7 @@ class Memo < ApplicationRecord
has_many :memo_tag_repertoires, dependent: :destroy has_many :memo_tag_repertoires, dependent: :destroy
has_many :tag_repertoires, :through => :memo_tag_repertoires has_many :tag_repertoires, :through => :memo_tag_repertoires
has_many :praise_tread, as: :praise_tread_object, dependent: :destroy has_many :praise_treads, as: :praise_tread_object, dependent: :destroy
has_one :praise_tread_cache, as: :object, dependent: :destroy has_one :praise_tread_cache, as: :object, dependent: :destroy
belongs_to :author, class_name: 'User', foreign_key: 'author_id' belongs_to :author, class_name: 'User', foreign_key: 'author_id'
@ -14,6 +14,7 @@ class Memo < ApplicationRecord
has_many :descendants, foreign_key: :root_id, class_name: 'Memo' has_many :descendants, foreign_key: :root_id, class_name: 'Memo'
has_many :children, foreign_key: :parent_id, class_name: 'Memo' has_many :children, foreign_key: :parent_id, class_name: 'Memo'
has_many :attachments, as: :container, dependent: :destroy
scope :field_for_list, lambda{ scope :field_for_list, lambda{
select([:id, :subject, :author_id, :sticky, :updated_at, :language, :reward, :all_replies_count, :viewed_count, :forum_id]) select([:id, :subject, :author_id, :sticky, :updated_at, :language, :reward, :all_replies_count, :viewed_count, :forum_id])

@ -440,7 +440,7 @@ class User < ApplicationRecord
end end
def manager_of_memo?(memo) def manager_of_memo?(memo)
id == memo.author_id || admin? id == memo.author_id || admin? || business?
end end
# 是否是项目管理者 # 是否是项目管理者

@ -148,18 +148,29 @@ class DiscussesService
@discuss = Discuss.select([:id, :hidden, :reward, :dis_type, :dis_id, :position, :challenge_id, :root_id]).find(id) @discuss = Discuss.select([:id, :hidden, :reward, :dis_type, :dis_id, :position, :challenge_id, :root_id]).find(id)
end end
protected def recommends
hot_shixuns = Shixun.field_for_recommend.published.order("myshixuns_count desc").limit(2)
newest_shixuns = Shixun.field_for_recommend.published.order("created_at desc").limit(2)
recommend_shixuns = []
hot_shixuns.each do |hs|
recommend_shixuns << {:id => hs.id, :name => hs.name, :identifier => hs.identifier, :myshixuns_count => hs.myshixuns_count, :image_url => url_to_avatar(hs)}
end
newest_shixuns.each do |ns|
recommend_shixuns << {:id => ns.id, :name => ns.name, :identifier => ns.identifier, :myshixuns_count => ns.myshixuns_count, :image_url => url_to_avatar(ns)}
end
return recommend_shixuns
end
def memo_list memos def memo_list memos
memos.map do |m| memos.map do |m|
user = User.find(m.user_id) user = m.user
praise_count = m.praise_tread.where(:praise_or_tread => 1).count # praise_count = m.praise_treads.select{|pt| pt.praise_or_tread == 1}.count
replies_count = Discuss.where(:root_id => m.id).count replies_count = m.child_discuss_count
shixun_tag = m.dis.tag_repertoires.map(&:name) shixun_tag = m.dis.tag_repertoires.map(&:name)
m.attributes.dup.except("user_id", "dis_id", "dis_type", "root_id").merge({ m.attributes.dup.except("user_id", "dis_id", "dis_type", "root_id", "praise_count", "content").merge({
subject: (message_content m.content), subject: (message_content m.content),
username: user.show_name, username: user.full_name,
login: user.login, login: user.login,
praise_count: praise_count,
replies_count: replies_count, replies_count: replies_count,
image_url: url_to_avatar(user), image_url: url_to_avatar(user),
shixun_tag: shixun_tag, shixun_tag: shixun_tag,
@ -168,23 +179,12 @@ class DiscussesService
end end
end end
protected
def format_for_current_user current_user def format_for_current_user current_user
{username: current_user.show_name, login: current_user.login, user_id: current_user.id, image_url: url_to_avatar(current_user), admin: current_user.admin?} {username: current_user.show_name, login: current_user.login, user_id: current_user.id, image_url: url_to_avatar(current_user), admin: current_user.admin?}
end end
def recommends
hot_shixuns = Shixun.field_for_recommend.published.order("myshixuns_count desc").limit(2)
newest_shixuns = Shixun.field_for_recommend.published.order("created_at desc").limit(2)
recommend_shixuns = []
hot_shixuns.each do |hs|
recommend_shixuns << {:id => hs.id, :name => hs.name, :identifier => hs.identifier, :myshixuns_count => hs.myshixuns_count, :image_url => url_to_avatar(hs)}
end
newest_shixuns.each do |ns|
recommend_shixuns << {:id => ns.id, :name => ns.name, :identifier => ns.identifier, :myshixuns_count => ns.myshixuns_count, :image_url => url_to_avatar(ns)}
end
return recommend_shixuns
end
# 将数据库对象转换成哈希对象 # 将数据库对象转换成哈希对象
def object_to_hash objects def object_to_hash objects
objects.map{|o| o.attributes.dup} objects.map{|o| o.attributes.dup}

@ -3,7 +3,7 @@ class PrivateMessages::CreateService < ApplicationService
attr_reader :sender, :receiver, :params attr_reader :sender, :receiver, :params
def initialize(sender, receiver, **params) def initialize(sender, receiver, params)
@sender = sender @sender = sender
@receiver = receiver @receiver = receiver
@params = params @params = params

@ -0,0 +1,27 @@
json.memo_list @memos
# do |memo|
# json.(memo, :id, :updated_at, :reward)
# json.subject message_content(memo.content)
# json.praise_count memo.praises_count
# json.replies_count memo.child_discuss_count
# json.shixun_tag memo.dis.tag_repertoires.map(&:name)
# json.username memo.user.full_name
# json.login memo.user.login
# json.image_url url_to_avatar(memo.user)
# json.tpm_url "/shixuns/#{memo.dis.identifier}/shixun_discuss"
# end
json.memo_count @memo_count
json.hot_memos do
json.array! @hot_memos do |hm|
json.(hm, :id, :subject, :language, :forum_id)
json.replies_count hm.all_replies_count
# json.praise_count hm.praise_tread.praise_count
json.tag hm.tag_repertoires.map(&:name)
end
end
json.hot_tags @hot_tags
json.recommend_shixuns @recommend_shixuns

@ -10,7 +10,7 @@ json.hidden message.hidden
if message.m_parent_id if message.m_parent_id
json.can_delete message.can_delete(identity) json.can_delete message.can_delete(identity)
else else
json.praise_count message.praise_treads.liker.count json.praise_count message.praise_treads.select{|pt| pt.praise_or_tread == 1}.count
json.user_praise message.praise_treads.user_liker(current_user).count json.user_praise message.praise_treads.select{|pt| pt.praise_or_tread == 1 && user_id == current_user.id}.count
json.child_message_count message.m_reply_count json.child_message_count message.m_reply_count
end end

@ -3,6 +3,5 @@ json.(memo, :id, :subject, :is_md, :content, :sticky, :reward, :viewed_count)
json.tag memo.tag_repertoires.map(&:name) json.tag memo.tag_repertoires.map(&:name)
json.time memo.created_at json.time memo.created_at
json.replies_count memo.all_replies_count json.replies_count memo.all_replies_count
json.attachments_list [] json.user_praise memo.praise_treads.user_liker(@user.try(:id)) ? true : false
json.user_praise memo.praise_tread.user_liker(@user.try(:id)) ? true : false json.memo_praise_count memo.praise_treads.liker.count
json.memo_praise_count = memo.praise_tread.liker.count

@ -1,7 +1,7 @@
json.(memo, :id, :subject, :author_id, :sticky, json.(memo, :id, :subject, :author_id, :sticky,
:updated_at, :language, :reward, :all_replies_count, :updated_at, :language, :reward, :all_replies_count,
:viewed_count, :forum_id) :viewed_count, :forum_id)
json.praise_count memo.praise_tread.praise_count json.praise_count memo.praise_treads.liker.count
json.replies_count memo.all_replies_count json.replies_count memo.all_replies_count
json.tag memo.tag_repertoires.map(&:name) json.tag memo.tag_repertoires.map(&:name)
json.user_name memo.author.full_name json.user_name memo.author.full_name

@ -7,8 +7,8 @@ json.username memo.author.full_name
json.reward memo.reward json.reward memo.reward
json.hidden memo.hidden json.hidden memo.hidden
json.permission @user.manager_of_memo?(memo) json.permission @user.manager_of_memo?(memo)
json.praise_count memo.praise_tread.liker.count json.praise_count memo.praise_treads.select{|pt| pt.praise_or_tread == 1}.count
json.user_praise memo.praise_tread.select{|pt| pt.user_id == @user.id}.length > 0 json.user_praise memo.praise_treads.select{|pt| pt.praise_or_tread == 1 && pt.user_id == @user.id}.length > 0
json.user_login memo.author.login json.user_login memo.author.login
json.admin @user.admin json.admin @user.admin

@ -0,0 +1,7 @@
json.(@memo, :subject, :content, :forum_id)
json.memo_tags @memo_tags
json.attachments @attachments do |attachment|
json.partial! "attachments/attachment_simple", locals: {attachment: attachment}
end
json.tag_list @tag_list
json.forums forum_list

@ -8,22 +8,30 @@
# tidding_count: 消息数 # tidding_count: 消息数
# # # #
json.memo_list do json.memo_list @memos do |memo|
json.array! @memos do |memo| json.(memo, :id, :subject, :sticky,
json.partial! "memos/memo_list", locals: {memo: memo} :updated_at, :language, :reward,
end :viewed_count, :forum_id)
json.praise_count memo.praise_treads.select{|pt| pt.praise_or_tread == 1}.count
json.replies_count memo.all_replies_count
json.tag memo.tag_repertoires.map(&:name)
json.user_name memo.author.full_name
json.login memo.author.login
json.image_url url_to_avatar(memo.author)
end end
json.memo_count @memos_count json.memo_count @memos_count
json.hot_memos do json.hot_memos do
json.array! @hot_memos do |hm| json.array! @hot_memos do |hm|
json.(hm, :id, :subject, :language, :forum_id, :all_replies_count) json.(hm, :id, :subject, :language, :forum_id)
json.replies_count hm.all_replies_count json.replies_count hm.all_replies_count
json.praise_count hm.praise_tread.praise_count # json.praise_count hm.praise_tread.praise_count
json.tag hm.tag_repertoires.map(&:name) json.tag hm.tag_repertoires.map(&:name)
end end
end end
json.hot_tags @tags_info.map{|o| o.attributes.dup.except("cnt", "id")} json.hot_tags @tags_info.map{|o| o.attributes.dup.except("cnt", "id")}
json.recommend_shixuns @recommend_shixuns

@ -1,3 +1,2 @@
json.tag_list @tag_list json.tag_list @tag_list
json.forums @csrf_token json.forums forum_list

@ -1,5 +1,9 @@
json.partial! "memos/memo", memo: @memo json.partial! "memos/memo", memo: @memo
json.attachments_list @attachments do |attachment|
json.partial! "attachments/attachment_simple", locals: {attachment: attachment}
end
json.memo_replies do json.memo_replies do
json.array! @memos do |memo| json.array! @memos do |memo|
json.partial! "memos/replies_list", memo: memo json.partial! "memos/replies_list", memo: memo
@ -9,10 +13,11 @@ end
json.author_info do json.author_info do
json.username @memo.author.full_name json.username @memo.author.full_name
# TODO watched_by 插件没法用,等把lib文件载入后在打开代码 # TODO watched_by 插件没法用,等把lib文件载入后在打开代码
#json.watched @memo.author.watched_by?(@user) json.watched @user.watched?(@memo.author)
json.image_url url_to_avatar(@memo.author) json.image_url url_to_avatar(@memo.author)
json.identity @memo.author.identity json.identity @memo.author.identity
json.login @memo.author.login json.login @memo.author.login
json.user_id @memo.author.id json.user_id @memo.author.id
end end
json.recommend_shixuns @recommend_shixuns

@ -1,4 +1,5 @@
json.username @user.full_name json.username @user.full_name
json.real_name @user.real_name
json.login @user.login json.login @user.login
json.user_id @user.id json.user_id @user.id
json.image_url url_to_avatar(@user) json.image_url url_to_avatar(@user)

@ -20,7 +20,16 @@ Rails.application.routes.draw do
put 'commons/unhidden', to: 'commons#unhidden' put 'commons/unhidden', to: 'commons#unhidden'
delete 'commons/delete', to: 'commons#delete' delete 'commons/delete', to: 'commons#delete'
resources :memos resources :memos do
member do
end
collection do
end
end
resources :tem_tests resources :tem_tests
# For details on the DSL available within this file, see http://guides.rubyonrails.org/routing.html # For details on the DSL available within this file, see http://guides.rubyonrails.org/routing.html
# #
@ -222,6 +231,7 @@ Rails.application.routes.draw do
resources :discusses do resources :discusses do
collection do collection do
get :new_message get :new_message
get :forum_discusses
end end
member do member do

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

@ -288,20 +288,9 @@ class App extends Component {
<Trialapplicationreview {...this.props} {...this.state}></Trialapplicationreview> <Trialapplicationreview {...this.props} {...this.state}></Trialapplicationreview>
<Addcourses {...this.props} {...this.state}/> <Addcourses {...this.props} {...this.state}/>
<AccountProfile {...this.props} {...this.state}/> <AccountProfile {...this.props} {...this.state}/>
{/*{*/}
{/* isRender === true?*/}
{/* <LoginDialog></LoginDialog> : ""*/}
{/*}*/}
{/*{*/}
{/* isRenders === true?*/}
{/*<Trialapplication></Trialapplication>*/}
{/*:""*/}
{/*}*/}
<Router> <Router>
<Switch> <Switch>
{/*<Route path="/login" component={LoginRegisterPage}/>*/}
{/*众包创新*/} {/*众包创新*/}
<Route path={"/crowdsourcings"} component={ProjectPackages}/> <Route path={"/crowdsourcings"} component={ProjectPackages}/>
@ -327,9 +316,7 @@ class App extends Component {
render={ render={
(props) => (<UsersInfo {...this.props} {...props} {...this.state} />) (props) => (<UsersInfo {...this.props} {...props} {...this.state} />)
}></Route> }></Route>
{/*<Route*/}
{/* path="/trialapplication" component={Trialapplication}*/}
{/*/>*/}
<Route <Route
path="/changepassword" component={EducoderLogin} path="/changepassword" component={EducoderLogin}
/> />
@ -349,14 +336,6 @@ class App extends Component {
{/*列表页*/} {/*列表页*/}
<Route path="/shixuns" component={TPMShixunsIndexComponent}/> <Route path="/shixuns" component={TPMShixunsIndexComponent}/>
{/* <Route path="/shixunchild" component={TPMShixunchildIndexComponent}>
</Route>
<Route path="/fork_list" component={TPMshixunfork_listIndexComponent}>
</Route> */}
{/*<Route path="/forums" component={ForumsIndexComponent}>*/}
{/*</Route>*/}
{/*实训课程(原实训路径)*/} {/*实训课程(原实训路径)*/}
<Route path="/paths" component={ShixunPaths}></Route> <Route path="/paths" component={ShixunPaths}></Route>
@ -370,16 +349,9 @@ class App extends Component {
{/*课堂*/} {/*课堂*/}
<Route path="/courses" component={CoursesIndex} {...this.props}></Route> <Route path="/courses" component={CoursesIndex} {...this.props}></Route>
{/* 课堂讨论 */} {/* <Route path="/forums" component={ForumsIndexComponent}>
{/* <Route path="/board" component = {BoardIndex} {...this.props}></Route> */}
{/* <Route path="/tpforums" component={TPForumsIndexComponent}>
</Route> */} </Route> */}
{/* <Route path="/myshixuns/:shixunId/stages/:stageId" component={Index}/> */}
{/* 兴趣页面*/}
{/*<Route path="/interest" component={Interestpage}/>*/}
<Route path="/comment" component={CommentComponent}/> <Route path="/comment" component={CommentComponent}/>
<Route path="/testMaterial" component={TestMaterialDesignComponent}/> <Route path="/testMaterial" component={TestMaterialDesignComponent}/>
<Route path="/test" component={TestIndex}/> <Route path="/test" component={TestIndex}/>
@ -387,14 +359,9 @@ class App extends Component {
<Route path="/testRCComponent" component={TestComponent}/> <Route path="/testRCComponent" component={TestComponent}/>
<Route path="/testUrlQuery" component={TestUrlQueryComponent}/> <Route path="/testUrlQuery" component={TestUrlQueryComponent}/>
{/* <Route component={NotFoundPage}/> */}
{/*列表页*/}
{/*<Route component={TPMShixunsIndexComponent}/>*/}
{/*首页*/}
<Route exact path="/" component={ShixunsHome}/> <Route exact path="/" component={ShixunsHome}/>
<Route component={Shixunnopage}/> <Route component={Shixunnopage}/>
{/*<Route component={ShixunsHome}/>*/}
</Switch> </Switch>
</Router> </Router>

@ -0,0 +1,79 @@
import React,{ Component } from "react";
import { getUrl2 } from "educoder";
const $ = window.$
let _url_origin = getUrl2()
class Clappr extends Component{
constructor(props){
super(props);
this.state={
}
}
componentDidMount() {
const source = this.props.source || "http://your.video/here.mp4"
const { id } = this.props
const _id = `#_player${id}`
if (window['Clappr']) {
const player = new window.Clappr.Player({
source: source, parentId: _id,
plugins: {
'core': [window.Clappr.MediaControl, window.Clappr.Playback]
}
});
} else {
$.getScript(
`${_url_origin}/javascripts/media/clappr.min.js`,
(data, textStatus, jqxhr) => {
window.clappr = window.Clappr
$.getScript(
`${_url_origin}/javascripts/media/clappr-playback-rate-plugin.min.js`,
(data, textStatus, jqxhr) => {
const player = new window.Clappr.Player({
source: source, parentId: _id,
plugins: {
'core': [window.Clappr.MediaControl, window['clappr-playback-rate-plugin'].default]
}
});
})
});
//
// $.when(
// $.getScript( `${_url_origin}/javascripts/media/clappr.min.js` ),
// // $.getScript( `${_url_origin}/javascripts/media/clappr-thumbnails-plugin.js` ),
// $.getScript( `${_url_origin}/javascripts/media/clappr-playback-rate-plugin.min.js` ),
// $.Deferred(function( deferred ){
// $( deferred.resolve );
// })
// ).done(function(){
// //place your code here, the scripts are all loaded
// const player = new window.Clappr.Player({
// source: source, parentId: _id,
// plugins: {
// 'core': [window.Clappr.MediaControl, window.Clappr.Playback]
// }
// });
// });
}
}
render(){
let { source, id, className } = this.props;
const _id = `_player${id}`
return(
<React.Fragment>
<style>{`
.playback_rate {
margin-right: 16px;
}
`}</style>
<div id={_id} className={className}></div>
</React.Fragment>
)
}
}
export default Clappr;

@ -53,6 +53,8 @@ export { default as MarkdownToHtml } from './components/markdown/MarkdownToHtml'
export { default as DMDEditor } from './components/markdown/DMDEditor' export { default as DMDEditor } from './components/markdown/DMDEditor'
export { default as Clappr } from './components/media/Clappr'
export { default as ImageLayerHook } from './hooks/ImageLayerHook' export { default as ImageLayerHook } from './hooks/ImageLayerHook'

@ -0,0 +1,50 @@
import React, { Component } from 'react';
class EffectDisplayContent extends Component {
constructor(props) {
super(props)
this.state = {
}
}
render() {
const { typeName, content1, content2, content3 } = this.props;
return (
<div className="task-popup-content effectDisplay">
<style>{`
.effectDisplay .content_title {
flex: 1 1 0
}
.effectDisplay .content>div {
flex: 1
}
.effectDisplay .clappr {
display: flex;
justify-content: center;
}
.effectDisplay .clappr>div {
width: 400px !important;
}
`}</style>
<div className="clearfix df">
{content1 && <p className="content_title edu-txt-center fl mr03precent font-18">原始{typeName}</p>}
{content2 && <p className="content_title edu-txt-center fl font-18 mr03precent">实际输出{typeName}</p>}
{content3 && <p className="content_title edu-txt-center fl font-18 mr03precent">预期输出{typeName}</p>}
</div>
<div className="clearfix df content" >
{content1 && <div className="fl mr03precent pt10 mb50">
{content1}
</div>}
{content2 && <div className="fl mr03precent pt10 mb50">
{content2}
</div>}
{content3 && <div className="fl mr03precent pt10 mb50">
{content3}
</div>}
</div>
</div>
);
}
}
export default EffectDisplayContent;

@ -2,9 +2,9 @@ import React, { Component } from 'react';
import { Redirect } from 'react-router'; import { Redirect } from 'react-router';
import PropTypes from 'prop-types'; import PropTypes from 'prop-types';
import { Clappr } from 'educoder'
import axios from 'axios'; import axios from 'axios';
import EffectDisplayContent from './EffectDisplayContent'
class EvaluateSuccessEffectDisplay extends Component { class EvaluateSuccessEffectDisplay extends Component {
constructor(props) { constructor(props) {
super(props) super(props)
@ -35,7 +35,8 @@ class EvaluateSuccessEffectDisplay extends Component {
// qrcode // qrcode
// const type = 'image' // 'qrcode' // const type = 'image' // 'qrcode'
const { type, qrcode_str, const { type, qrcode_str,
answer_picture, orignal_picture, user_picture, contents } = this.props; answer_picture, orignal_picture, user_picture, contents,
user_file, answer_file, orignal_file } = this.props;
if (type == 'qrcode') { if (type == 'qrcode') {
// 单张图片比如安卓评测完显示qrcode // 单张图片比如安卓评测完显示qrcode
return ( return (
@ -54,22 +55,35 @@ class EvaluateSuccessEffectDisplay extends Component {
return ( return (
<div className="task-popup-content"> <div className="task-popup-content">
<div className="clearfix"> <div className="clearfix">
<p className="edu-txt-center fl with33 mr03precent font-18">原始图片</p> {orignal_picture[0] && <p className="edu-txt-center fl with33 mr03precent font-18">原始图片</p>}
<p className="edu-txt-center fl font-18 with33 mr03precent">实际输出图片</p> <p className="edu-txt-center fl font-18 with33 mr03precent">实际输出图片</p>
<p className="edu-txt-center fl font-18 with33 mr03precent">预期输出图片</p> <p className="edu-txt-center fl font-18 with33 mr03precent">预期输出图片</p>
</div> </div>
<div className="clearfix" id="picture-content"> <div className="clearfix" id="picture-content">
{orignal_picture[0] && <div className="fl with33 mr03precent pt10 mb50">
{orignal_picture.map(item => {
return (
<img alt="Icon"
src={ item.pic_url}/> )
})}
{/* {orignal_picture[0] && <img alt="Icon"
src={ orignal_picture[0].pic_url}/>} */}
</div>}
<div className="fl with33 mr03precent pt10 mb50"> <div className="fl with33 mr03precent pt10 mb50">
{orignal_picture[0] && <img alt="Icon" {user_picture.map(item => {
src={ orignal_picture[0].pic_url}/>} return (
</div> <img alt="Icon"
<div className="fl with33 mr03precent pt10 mb50"> src={ item.pic_url}/> )
{user_picture[0] && <img alt="Icon" })}
src={ user_picture[0].pic_url }/>}
</div> </div>
<div className="fl with33 mr03precent pt10 mb50"> <div className="fl with33 mr03precent pt10 mb50">
{ answer_picture[0] && <img alt="Icon" {answer_picture.map(item => {
src={ answer_picture[0].pic_url}/> } return (
<img alt="Icon"
src={ item.pic_url}/> )
})}
{/* { answer_picture[0] && <img alt="Icon"
src={ answer_picture[0].pic_url}/> } */}
</div> </div>
</div> </div>
</div> </div>
@ -88,6 +102,30 @@ class EvaluateSuccessEffectDisplay extends Component {
return ( return (
<iframe id="_displayIframe"></iframe> <iframe id="_displayIframe"></iframe>
) )
} else if (type == 'mp3') {
return (
<EffectDisplayContent
typeName="音频"
content1={ orignal_file[0] && orignal_file[0].file_url
? <Clappr source={orignal_file[0].file_url} id="1" className="clappr"></Clappr> : null }
content2={ user_file[0] && user_file[0].file_url
? <Clappr source={user_file[0].file_url} id="2" className="clappr"></Clappr> : null }
content3={ answer_file[0] && answer_file[0].file_url
? <Clappr source={answer_file[0].file_url} id="3" className="clappr"></Clappr> : null }
></EffectDisplayContent>
)
} else if (type == 'mp4') {
return (
<EffectDisplayContent
typeName="视频"
content1={ orignal_file[0] && orignal_file[0].file_url
? <Clappr source={orignal_file[0].file_url} id="1" className="clappr"></Clappr> : null }
content2={ user_file[0] && user_file[0].file_url
? <Clappr source={user_file[0].file_url} id="2" className="clappr"></Clappr> : null }
content3={ answer_file[0] && answer_file[0].file_url
? <Clappr source={answer_file[0].file_url} id="3" className="clappr"></Clappr> : null }
></EffectDisplayContent>
)
} }
/* <div className="with49 fr"> /* <div className="with49 fr">

Loading…
Cancel
Save