AutoMount (Python)Среда, Июль 13, 2011 г. Монтирую с помощью sshfs и curlftpfs, в зависимости от типа доступа. Всё хорошо, да вот только аккаунтов накопилась целая куча из которых постоянно используемых чуть больше десятка. Ручное монтирование стало утомлять. Это необходимо каждый раз создать точку, вспомнить или отыскать реквизиты доступа, набить команду... Ничто так не отравляет позитивный настрой к работе как самая обыденная рутина. И вот однажды когда в очередной раз я забыл где у меня записаны доступы к нужному аккаунту, я твёрдо решил навести порядок. А точнее автоматизировать это безобразие. Решил написать программу которая будет управлять подключениями, создавать точки, монтировать, отмонтировать, помнить реквизиты. Для начала я определился с задачами:
Вот и всё, спартанский минимум для начала, без пыхтелок и рюшечек. Конфигурационный файл я решил сделать в стиле виндовского ini, но обозвал его .netmount.conf и поместил в домашнюю директорию. Выглядит он примерно так: [options] path = /mnt comm_umount = fusermount -u -z comm_ssh_mount = sshfs comm_ftp_mount = curlftpfs [akk1] type = ssh url = bla1.ru user = root passwd = q7EVNrCpNR [akk2] type = ssh url = bla2.ru user = root passwd = 7lnlBzhYh3 [akk3] type = ftp url = bla3.ru user = root passwd = В секции [options] настройки самой прграммы, думаю там всё понятно. Далее секции соответствуют аккаунтам. Все поля обязательны для заполнения, единственное необязательное это пароль, его ведь может и не быть. Заголовок секции — имя аккаунта. Из этих имён будет состоять список при запуске без аргументов. Также одно из этих имён необходимо передать для монтирования в качестве аргумента. Точка монтирования будет создана с таким же именем. Вот программа :
#!/usr/bin/python2
# -*- coding: utf-8 -*-
import sys
import os
from ConfigParser import ConfigParser
from subprocess import Popen, PIPE
config = ConfigParser()
config.read(os.path.expanduser("~")+"/.netmount.conf")
sections = config.sections()
try:
sections.remove("options")
except:
print "Конфигурационный файл не валиден\n[options]"
sys.exit(1)
f = open("/etc/mtab")
mtab = f.read()
f.close()
def is_mount(mp):
"примонтирован ли путь"
if mp in mtab:
return True
return False
# основные опции
options = {}
try:
options["path"] = config.get("options", "path").strip()
options["comm_umount"] = config.get("options", "comm_umount").strip()
options["comm_ssh_mount"] = config.get("options", "comm_ssh_mount").strip()
options["comm_ftp_mount"] = config.get("options", "comm_ftp_mount").strip()
if len(filter(lambda x: len(x)==0, options.values())) > 0:
raise ValueError
except:
print "Конфигурационный файл не валиден\n[options]"
sys.exit(1)
# аргументы
if len(sys.argv) < 2:
for s in sections:
if is_mount(options["path"]+"/"+s):
print "+"+s
else:
print "-"+s
sys.exit(0)
elif not sys.argv[1] in sections:
print "Для '"+sys.argv[1]+"' правило не задано"
sys.exit(1)
p = sys.argv[1]
# опции для точки монтирования
point = {}
try:
point["name"] = p
point["path"] = options["path"]+"/"+p
point["type"] = config.get(p, "type").strip()
point["url"] = config.get(p, "url").strip()
point["user"] = config.get(p, "user").strip()
point["passwd"] = config.get(p, "passwd").strip()
if len(point["type"]) == 0 or len(point["url"]) == 0 or len(point["user"]) == 0:
raise ValueError
except:
print "Конфигурационный файл не валиден\n["+p+"]"
sys.exit(1)
if point["type"] != "ftp" and point["type"] != "ssh":
print "Конфигурационный файл не валиден\n["+p+"] 'type' должен быть ftp или ssh"
sys.exit(1)
################################################
# ну вроде с конфигом всё как надо, едем дальше
################################################
# существует ли точка монтирования и примонтирована ли?
if os.path.isdir(point["path"]):
if is_mount(point["path"]):
if os.system(options["comm_umount"]+" "+point["path"]) > 0:
print p+" существует и примонтирован\nошибка при попытке отмонтировать."
sys.exit(1)
else:
os.rmdir(point["path"])
print p+" отмонтирован"
sys.exit(0)
os.rmdir(point["path"])
# создаём и монтируем
os.makedirs(point["path"], mode=0775)
if point["type"] == "ftp":
cmd = options["comm_ftp_mount"]+" ftp://"+point["user"]
if len(point["passwd"]) > 0:
cmd += ":"+point["passwd"]
cmd += "@"+point["url"]+" "+point["path"]
if os.system(cmd) == 0:
print p+" примонтирован"
elif point["type"] == "ssh":
cmd = options["comm_ssh_mount"]+" "+point["user"]+"@"+point["url"]+":/ "+point["path"]
if len(point["passwd"]) == 0:
if os.system(cmd) == 0:
print p+" примонтирован"
else:
cmd += " -o password_stdin"
proc = Popen(cmd, shell=True, stdin=PIPE, stdout=PIPE)
ans = proc.communicate(point["passwd"])
if ans[1] != None:
print ans[0]
else:
print p+" примонтирован"
Если что не понятно спрашивайте — разжую. Как по мне, так она простая. Возможно кто-то скажет что хранить доступы к разным серверам в открытом виде и одном месте не секьюрно. Да это не совсем хорошо. Как вариант пароли или даже сам конфиг можно закриптовать. Можно воспользоваться каким либо менеджером паролей, Kwallet, GNOME Keyring или же другим аналогом в зависимости от предпочтений. При наличии прямых рук и желания, доработать будет не сложно. Если пригодится, пользуйтесь на здоровье :) | ||
Оставить коментарий
)
