persoconf/commands/add.py

135 lines
4.7 KiB
Python

#!/usr/bin/env python
# -*- coding: utf-8 -*-
import os.path
import utils
from metafile import Metafile, MalformedMetafileError, NoPathDefinedError
# --------------------------------------
def init(parser):
parser.add_argument( "app" ,
type=str ,
help="The app to add, or the app to add a conf " \
"file to" )
parser.add_argument( "conf" ,
nargs="?" ,
type=str ,
help="The conf file or directory to add to the app" )
parser.add_argument( "--confname" ,
type=str ,
help="A special name to save the conf " \
"file/directory in the persoconf directory" )
# --------------------------------------
def run(args, persoconf, logger):
# Check (and create) the app directory
appdir = os.path.join( persoconf.path, args.app )
if os.path.isdir(appdir):
if args.conf is None:
logger.warning("App '%s' already exists" % args.app)
exit()
elif os.path.exists(appdir):
logger.error( "The name '%s' is already used by a file in the " \
"persoconf directory"
% args.app)
exit()
else:
logger.info("Creating app '%s' in persoconf directory..." % args.app)
os.mkdir(appdir)
print("New app '%s' created in persoconf directory" % args.app)
if args.conf is None:
exit()
# Check that the conf file we are saving exists
if args.confname:
confname = args.confname
else:
confname = args.conf
# We need to remove trailing '/' because 'os.path.basename("toto/")'
# returns ''. And that's not cool.
while confname[-1] == os.path.sep :
confname = confname[:-1] # Remove trailing slashes
confname = os.path.basename(confname)
# Remove leading dots, so the name under which the conffile is saved is
# not hidden.
while confname[0] == ".":
confname = confname[1:] # Remove leading dots
confpath = appdir + "/" + confname
# Load app META file
try:
appmeta = Metafile( json_path = os.path.join( appdir ,
persoconf.metafile ) )
except FileNotFoundError:
logger.info( "Metafile %s does not exist for app %s"
% (persoconf.metafile, args.app) )
appmeta = Metafile( name=args.app )
appmeta.json_path = os.path.join( persoconf.path ,
args.app ,
persoconf.metafile )
except MalformedMetafileError:
logger.error( "Malformed metafile %s in app %s"
% (persoconf.metafile, args.app) )
exit(1)
# Check that the file is really new
absconf = utils.contractuser(
os.path.abspath(os.path.expanduser(args.conf))
)
try:
dstdic = appmeta.get_files_dst2src()
except MalformedMetafileError:
logger.error( "Malformed metafile %s in app %s"
% (persoconf.metafile, args.app) )
exit(1)
if absconf in dstdic:
logger.error( "File %s already exists as %s in app %s"
% (absconf, dstdic[absconf], args.app) )
exit(1)
# Copy the file (or directory)
if utils.copy_file_or_directory( logger ,
path_dst=confpath ,
path_src=args.conf,
overwrite=False ):
logger.info( "New conf file or directory '%s' associated with app '%s'"
% (confname, args.app))
else:
logger.error( "Failed to copy file or directory %s" % args.conf)
exit(1)
# Add the file to META: first update META data
logger.debug( "adding meta data for %s in %s" % (confname, args.app) )
appmeta.add_file( confname, dest=absconf )
# Then write to the metafile
try:
logger.debug("Writing to metafile")
appmeta.save()
except NoPathDefinedError:
logger.error( "Unable to save json Metafile for app %s : no path " \
"defined"
% appmeta.name )
exit(1)