Actually calling shell commands from a managed code is not a very bad idea. They are reliable, very well tested and mostly lightweight and sometimes just a wrapper around kernel or other modules function. This is also seems to be the same method Node.js modules use when they want to access something lowlevel or related to networking. For example see this source code: node-wireless/node_modules/wireless/index.js
If you don't like it this way there is always "Interop". The same way that you can DllImport() libraries in Windows, you can do in Linux. See here: http://www.mono-project.com/Interop_with_Native_Libraries
IMHO the second solution doesn't worth the effort. Calling shell commands is elegant and neat enough.