SNMP View: Allow/Deny OIDs

A default SNMP agent is chatty. Ask it nicely and it will read out your whole MIB tree — every process name, every mounted filesystem, every network interface — to anyone holding the community string. An SNMP view OID rule is how you shut that down. Instead of exposing the entire tree, you hand out a short allowlist: these OIDs and nothing else. This page covers exactly that — the view directive in snmpd.conf, how to allow or deny specific OIDs, how to wire the view into an access rule, and how to prove it worked before anything external starts polling.

Prerequisites

Before you touch a view, a few things need to be in place:

  • A running SNMPv2c agent (Net-SNMP's snmpd) on the host you want to lock down. If it isn't installed yet, start with install snmpd on Ubuntu/Debian or CentOS/RHEL.
  • Root or sudo accesssnmpd.conf lives in a system directory and the service restart needs privileges.
  • The main config file at /etc/snmp/snmpd.conf, plus a text editor you're comfortable with.
  • A read-only community string already defined (the com2sec line). If you haven't set one, pair this with secure your community string.
  • A second machine, or the same box, with Net-SNMP client tools (snmpwalk, snmpget) so you can test. See Net-SNMP tools.

That's the whole list. You don't need SNMPv3 for this — views work the same across versions — though v3 layers authentication on top, which is a separate hardening step.

Step-by-step

Here's the part that actually matters. A view in Net-SNMP is a named set of OID subtrees, each flagged included or excluded. You build the set, then bind it to a group with an access line. Walk it through:

  1. Open the config as root:
    sudo nano /etc/snmp/snmpd.conf
    
  2. Name a view and add the first allowed OID. The syntax is view <name> <included|excluded> <subtree>. Start with host uptime:
    view    ReadData     included   .1.3.6.1.2.1.25.1.1.0
    
    That single line is your whole allowlist so far — one OID, hrSystemUptime, from the Host Resources MIB.
  3. Add one included line per OID you actually need. Only expose what your monitoring reads. A sensible read-only set for server health:
    view    ReadData     included   .1.3.6.1.2.1.25.1.1.0
    view    ReadData     included   .1.3.6.1.2.1.25.3.3.1.2
    view    ReadData     included   .1.3.6.1.2.1.25.2.3.1.3
    view    ReadData     included   .1.3.6.1.2.1.25.2.3.1.6
    view    ReadData     included   .1.3.6.1.4.1.2021.10.1.3
    
    Those cover uptime, CPU load, storage names, storage used, and system load respectively — see the sensor & OID catalog for what each one returns.
  4. Bind the view to your read group with an access line so the group can only see what the view allows:
    access  ReadGroup    ""    any    noauth   exact   ReadData   none   none
    
    Read access = ReadData; write and notify = none. Nobody writes anything.
  5. Save, then restart the daemon:
    sudo service snmpd restart
    

Prefer the broad-then-carve approach? You can include a whole subtree and exclude a branch under it. Include .1.3.6.1.2.1.25 (all Host Resources) but exclude the running-software table if you'd rather not leak process names. Net-SNMP resolves the longest matching prefix, so a specific excluded subtree beats a broader included one. Deny wins where it's more precise. Keep the allowlist tight and you shrink the attack surface to exactly the numbers your dashboards need.

Here's that allowlist line by line — every OID is real, read-only, and nothing else is exposed:

View line (OID)MIB objectWhat it exposes
.1.3.6.1.2.1.25.1.1.0hrSystemUptimeHost uptime
.1.3.6.1.2.1.25.3.3.1.2hrProcessorLoadPer-core CPU load
.1.3.6.1.2.1.25.2.3.1.3hrStorageDescrStorage / mount names
.1.3.6.1.2.1.25.2.3.1.6hrStorageUsedStorage used
.1.3.6.1.4.1.2021.10.1.3laLoadSystem load average

Configuration example

Here's a complete, annotated block that ties the community, group, and view together — the shape every locked-down agent ends up in:

# /etc/snmp/snmpd.conf — v2c read-only, allowlisted OIDs
agentAddress udp:161,udp6:[::1]:161        # change 161 to a random port for security

#       sec.name    source    community
com2sec ReadUser    default   <password>

#       group        sec.model  sec.name
group   ReadGroup    v2c        ReadUser

#       view         incl/excl  subtree
view    ReadData     included   .1.3.6.1.2.1.25.1.1.0
view    ReadData     included   .1.3.6.1.2.1.25.3.3.1.2
# ...one 'view ... included' line per allowed OID...

#       group        context  model  level   prefix  read      write  notify
access  ReadGroup    ""       any    noauth  exact   ReadData  none   none

Read it top to bottom and the logic is plain. com2sec maps a community string to a security name. group puts that name in a group. Each view line adds one OID to the allowlist. The final access line says: this group, over any model, with no auth, may read the ReadData view and do nothing else. Change the port on the agentAddress line while you're here — moving off the default trims noise from opportunistic scanners. The allocation-unit detail and full daemon toggles live in configure /etc/default/snmpd.

Annotated snmpd.conf showing view included lines building an SNMP view OID allowlist bound to a read group

Verify it works

Never trust a config you haven't tested. Two checks tell you everything.

First, confirm the daemon actually came back up:

service snmpd status

Then poll an OID that should be in the view, and one that shouldn't. An allowed OID returns a value:

snmpget -v2c -c <community> localhost 1.3.6.1.2.1.25.1.1.0

A denied OID — anything outside your included lines — comes back empty or with "No Such Object," which is exactly what you want. That silence is the allowlist doing its job. Walk the whole tree to see the full exposed surface at a glance:

snmpwalk -v2c -c <community> localhost .1

If that walk spills far more than your five or six OIDs, the view isn't bound — recheck that the access line references ReadData and not the built-in all view. Getting nothing at all usually points elsewhere; the SNMP troubleshooting guide covers timeouts and community mismatches.

Security note

An allowlist is a security control, so treat it like one:

  • Default-deny, then add. Start from nothing exposed and include only the OIDs your monitoring genuinely reads. Never ship the wide-open view all included .1.
  • Never expose write access. Keep write and notify set to none unless you have a hard requirement and SNMPv3 in front of it.
  • Exclude sensitive tables — running processes, installed software, ARP tables — if a downstream consumer doesn't need them.
  • Pair the view with a strong community string and a non-default port. A tight view with a guessable community is only half a lock. See secure the community string.
  • Prefer SNMPv3 where the wire can't be trusted; v2c sends the community in clear text (RFC 1901).

More depth on threat models and lockdown patterns lives in the security section.

Next: connect external monitoring

An allowlist decides what can be read. It doesn't decide who reads it or when. Local cron polling the OID is fine until the server itself falls over — then the very tool meant to warn you goes down with it. That's the gap external monitoring fills: an independent checker outside your network keeps polling your allowlisted OIDs on its own schedule and alerts you when the host goes quiet. It's the practical shape of double durability — notifications from a second, independent source instead of none.

ostr.io Monitoring is the zero-setup version of that: point it at your agent, list the OIDs you exposed here, and it fires real-time email and SMS alerts from outside. When you're ready, add an SNMP endpoint in ostr.io.

Diagram of an external monitor polling only allowlisted SNMP view OIDs through the agent over UDP 161

Frequently asked questions

What's the difference between view included and view excluded?

included adds a subtree to the allowlist; excluded removes one. Net-SNMP matches the most specific prefix, so an excluded subtree nested inside a broader included one is still hidden. Use included for a tight allowlist, and excluded to carve a sensitive branch out of an otherwise-broad grant.

Do I list every single OID, or can I use subtrees?

Either. A view line accepts a full leaf OID like .1.3.6.1.2.1.25.1.1.0 or a whole subtree like .1.3.6.1.2.1.25. Subtrees are convenient but expose everything beneath them, so favor specific OIDs when you can.

Why does my snmpwalk return nothing after adding a view?

Usually the view isn't bound to the group. Check that your access line names your view (ReadData) in the read column. A totally empty response can also mean a wrong community, port, or firewall — that's a troubleshooting matter, not a view one.

Does an OID allowlist work with SNMPv3?

Yes. Views are independent of version. With v3 you bind the view through a VACM access rule tied to an authenticated user instead of a v2c community, but the view ... included lines are identical.

Conclusion

Locking an SNMP agent down to a snmp view OID allowlist is a handful of lines: name a view, add one included entry per OID you truly need, and bind it to a read-only group with an access line. Test with snmpget against an allowed OID and a denied one, then let nothing outside that list leak. Pair the view with a strong community and a non-default port, and hand the exposed OIDs to an external monitor so a crashed server still raises its hand. Tight in, quiet out — that's the whole game.

Monitor it from outside the network

SNMP only tells you a box is healthy while something is still asking. ostr.io polls your endpoints externally and fires email + SMS alerts the moment a reading crosses your line — or the agent goes silent.