ytti/oxidized · error · KeyError
hook.channel is required
Error message
hook.channel is required
What it means
The slackdiff hook validates at startup that both token and channel keys exist in its config; a missing channel raises KeyError 'hook.channel is required' (lib/oxidized/hook/slackdiff.rb:11). The channel is where diffs are posted as snippets and where optional messages go (client.files_completeUploadExternal / chat.postMessage), so the token's bot/user must be able to post there.
Source
Thrown at lib/oxidized/hook/slackdiff.rb:11
require 'slack_ruby_client'
require 'uri'
require 'net/http'
# defaults to posting a diff, if messageformat is supplied them a message will be posted too
# diff defaults to true
class SlackDiff < Oxidized::Hook
def validate_cfg!
raise KeyError, 'hook.token is required' unless cfg.has_key?('token')
raise KeyError, 'hook.channel is required' unless cfg.has_key?('channel')
end
def slack_upload(client, title, content, channel, proxy)
logger.info "Posting diff as snippet to #{channel}"
upload_dest = client.files_getUploadURLExternal(filename: "change",
length: content.length,
snippet_type: "diff")
file_uri = URI.parse(upload_dest[:upload_url])
proxy_uri = URI.parse(proxy) if proxy
proxy_address = proxy_uri ? proxy_uri.host : :ENV
proxy_port = proxy_uri&.port
proxy_user = proxy_uri&.user
proxy_pass = proxy_uri&.password
http = Net::HTTP.new(file_uri.host, file_uri.port, proxy_address, proxy_port, proxy_user, proxy_pass)
http.use_ssl = true
View on GitHub (pinned to 687ed4262d)
Solutions
- Add the channel under the slackdiff hook block: channel: "#netdev-changes" (or a channel ID like C0123456789)
- Keep token and channel at the same indentation as the hook's other keys
- Restart oxidized so hook validation runs again
Example fix
# before
hooks:
slack:
type: slackdiff
token: xoxb-1234567890-abcdef
# after
hooks:
slack:
type: slackdiff
token: xoxb-1234567890-abcdef
channel: "#netdev-changes" Defensive patterns
Strategy: validation
Validate before calling
# check the slackdiff block before oxidized loads it
hook_cfg = YAML.load_file('/etc/oxidized/config')['hooks']['slack']
missing = %w[token channel].reject { |k| hook_cfg.key?(k) }
raise ArgumentError, "slackdiff config missing: #{missing.join(', ')}" unless missing.empty? Type guard
def slackdiff_cfg_valid?(cfg)
cfg.is_a?(Hash) && %w[token channel].all? { |k| cfg[k].is_a?(String) && !cfg[k].empty? }
end Try / catch
begin
hook.validate_cfg!
rescue KeyError => e
abort "fix the hooks config: #{e.message}"
end Prevention
- Prefer channel IDs (C0123456789) over names: they survive renames and are unambiguous
- Invite the bot to private channels; otherwise the post fails at runtime even though validation passed
- Key-check the hooks section in CI
When it happens
Trigger: A hooks block with type: slackdiff that sets token: but omits channel:, or a channel key lost to a typo or bad YAML indentation when the block was edited.
Common situations: Copying a partial example; renaming channel to room; reindenting the hooks block while adding messageformat/diff/proxy keys.
Related errors
- hook.token is required
- hook.remote_repo is required
- hook.jid is required
- hook.password is required
- hook.channel is required
AI-assisted analysis of ytti/oxidized@687ed4262d (2026-08-23).
Data as JSON: /api/errors/f14473ff5e76883b.
Report an issue: GitHub.