Prevent loops while moving

This commit is contained in:
karel.picman@lbcfree.net 2020-09-07 16:28:24 +02:00
parent 71075f26db
commit e935c04b7d
4 changed files with 55 additions and 0 deletions

View File

@ -96,6 +96,7 @@ class DmsfFolder < ActiveRecord::Base
validates_uniqueness_of :title, scope: [:dmsf_folder_id, :project_id, :deleted],
conditions: -> { where(deleted: STATUS_ACTIVE) }
validates :description, length: { maximum: 65535 }
validates :dmsf_folder, dmsf_folder_parent: true, if: Proc.new { |folder| !folder.new_record? }
before_create :default_values

View File

@ -0,0 +1,37 @@
# encoding: utf-8
# frozen_string_literal: true
#
# Redmine plugin for Document Management System "Features"
#
# Copyright © 2011-20 Karel Pičman <karel.picman@kontron.com>
#
# This program is free software; you can redistribute it and/or
# modify it under the terms of the GNU General Public License
# as published by the Free Software Foundation; either version 2
# of the License, or (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program; if not, write to the Free Software
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
class DmsfFolderParentValidator < ActiveModel::EachValidator
# Don't allow save folders with a parent pointing to the same folder
def validate_each(record, attribute, value)
folder = value
while folder
if folder == record
record.errors.add attribute, :invalid
return false
end
folder = folder.dmsf_folder
end
return true
end
end

View File

@ -29,6 +29,7 @@ DMSF_MAX_NOTIFICATION_RECEIVERS_INFO = 10
require_dependency File.dirname(__FILE__) + '/../app/validators/dmsf_file_name_validator'
require_dependency File.dirname(__FILE__) + '/../app/validators/dmsf_workflow_name_validator'
require_dependency File.dirname(__FILE__) + '/../app/validators/dmsf_url_validator'
require_dependency File.dirname(__FILE__) + '/../app/validators/dmsf_folder_parent_validator'
# Plugin's patches
require 'redmine_dmsf/patches/projects_helper_patch'

View File

@ -237,4 +237,20 @@ class DmsfFolderTest < RedmineDmsf::Test::UnitTest
assert DmsfFolder.find_by(project_id: @project2.id, title: @folder1.title)
end
def test_valid_parent
@folder2.dmsf_folder = @folder1
assert @folder2.save
end
def test_valid_parent_nil
@folder2.dmsf_folder = nil
assert @folder2.save
end
def test_valid_parent_loop
@folder1.dmsf_folder = @folder2
# @folder2 is under @folder1 => loop!
assert !@folder1.save
end
end