Disallow duplicate channels - providers can define which fields should be ‘unique’

This commit is contained in:
David Taylor 2017-07-28 15:47:46 +01:00
parent 11c8817ebd
commit ce8acc9c26
9 changed files with 31 additions and 9 deletions

View File

@ -36,12 +36,26 @@ class DiscourseChat::Channel < DiscourseChat::PluginModel
return
end
check_unique = false
matching_channels = DiscourseChat::Channel.all
data.each do |key, value|
regex_string = params.find{|p| p[:key] == key}[:regex]
if !Regexp.new(regex_string).match?(value)
errors.add(:data, "data.#{key} is invalid")
end
unique = params.find{|p| p[:key] == key}[:unique]
if unique
check_unique = true
matching_channels = matching_channels.with_data_value(key, value)
end
end
if check_unique && matching_channels.exists?
errors.add(:data, "matches an existing channel")
end
end
def rules

View File

@ -5,7 +5,7 @@ module DiscourseChat
PROVIDER_ENABLED_SETTING = :chat_integration_discord_enabled
CHANNEL_PARAMETERS = [
{key: "name", regex: '^\S+'},
{key: "webhook_url", regex: '^https:\/\/discordapp\.com\/api\/webhooks\/', hidden: true}
{key: "webhook_url", regex: '^https:\/\/discordapp\.com\/api\/webhooks\/', unique: true, hidden: true}
]
def self.send_message(url, message)

View File

@ -5,7 +5,7 @@ module DiscourseChat
PROVIDER_ENABLED_SETTING = :chat_integration_hipchat_enabled
CHANNEL_PARAMETERS = [
{key: "name", regex: '^\S+'},
{key: "webhook_url", regex: 'hipchat\.com', hidden:true},
{key: "webhook_url", regex: 'hipchat\.com', unique: true, hidden:true},
{key: "color", regex: '(yellow|green|red|purple|gray|random)'}
]

View File

@ -5,7 +5,7 @@ module DiscourseChat
PROVIDER_ENABLED_SETTING = :chat_integration_matrix_enabled
CHANNEL_PARAMETERS = [
{key: "name", regex: '^\S+'},
{key: "room_id", regex: '^\!\S+:\S+$', hidden:true}
{key: "room_id", regex: '^\!\S+:\S+$', unique: true, hidden:true}
]
def self.send_message(room_id, message)

View File

@ -4,7 +4,7 @@ module DiscourseChat
PROVIDER_NAME = "mattermost".freeze
PROVIDER_ENABLED_SETTING = :chat_integration_mattermost_enabled
CHANNEL_PARAMETERS = [
{key: "identifier", regex: '^[@#]\S*$'}
{key: "identifier", regex: '^[@#]\S*$', unique: true}
]
def self.send_via_webhook(message)

View File

@ -4,7 +4,7 @@ module DiscourseChat::Provider::SlackProvider
PROVIDER_ENABLED_SETTING = :chat_integration_slack_enabled
CHANNEL_PARAMETERS = [
{key: "identifier", regex: '^[@#]\S*$'}
{key: "identifier", regex: '^[@#]\S*$', unique: true}
]
def self.excerpt(post, max_length = SiteSetting.chat_integration_slack_excerpt_length)

View File

@ -5,7 +5,7 @@ module DiscourseChat
PROVIDER_ENABLED_SETTING = :chat_integration_telegram_enabled
CHANNEL_PARAMETERS = [
{key: "name", regex: '^\S+'},
{key: "chat_id", regex: '^(-?[0-9]+|@\S+)$'}
{key: "chat_id", regex: '^(-?[0-9]+|@\S+)$', unique: true}
]
def self.setup_webhook

View File

@ -48,7 +48,7 @@ RSpec.shared_context "validated dummy provider" do
PROVIDER_NAME = "dummy2".freeze
PROVIDER_ENABLED_SETTING = :chat_integration_enabled # Tie to main plugin enabled setting
CHANNEL_PARAMETERS = [
{key: "val", regex: '^\S+$'}
{key: "val", regex: '^\S+$', unique: true}
]
@@sent_messages = []

View File

@ -24,7 +24,7 @@ RSpec.describe DiscourseChat::Channel do
it 'can be filtered by provider' do
channel1 = DiscourseChat::Channel.create!(provider:'dummy')
channel2 = DiscourseChat::Channel.create!(provider:'dummy2', data:{val:"blah"})
channel3 = DiscourseChat::Channel.create!(provider:'dummy2', data:{val:"blah"})
channel3 = DiscourseChat::Channel.create!(provider:'dummy2', data:{val:"blah2"})
expect(DiscourseChat::Channel.all.length).to eq(3)
@ -64,7 +64,6 @@ RSpec.describe DiscourseChat::Channel do
end
describe 'validations' do
let(:channel) { }
it 'validates provider correctly' do
channel = DiscourseChat::Channel.create!(provider:"dummy")
@ -93,5 +92,14 @@ RSpec.describe DiscourseChat::Channel do
expect(channel2.valid?).to eq(false)
end
it 'disallows duplicate channels' do
channel1 = DiscourseChat::Channel.create(provider:"dummy2", data:{val:"hello"})
channel2 = DiscourseChat::Channel.new(provider:"dummy2", data:{val:"hello"})
expect(channel2.valid?).to eq(false)
channel2.data[:val] = "hello2"
expect(channel2.valid?).to eq(true)
end
end
end