change current working directory

811 views
Skip to first unread message

Alex Arshavski

unread,
May 13, 2012, 9:18:39 AM5/13/12
to salt-...@googlegroups.com
Hi,

I wrote some module where I want to run some command to change current working directory.
For example when I untar some archive I want to know where it's unpacked, so I want to change cwd before that.
How can I do that inside module?

Thanks, Arshavski Alexander.

Thomas S Hatch

unread,
May 13, 2012, 11:39:56 AM5/13/12
to salt-...@googlegroups.com
You can do this a number of ways safely. First off, when you call a shell out command you should use the cmd module to call the command, aka:
__salt__['cmd.run']('command')

one of the options you can pass here is cwd, to change the cwd of the command.

Also, you can safely use the python os library to change the cwd via the os.chdir function. Keep in mind that it you do this, the frugal thing to do it change back to the old cwd when you are done

Alex Arshavski

unread,
May 13, 2012, 2:43:35 PM5/13/12
to salt-...@googlegroups.com
Cool. Thanks a lot.

Alex Arshavski

unread,
May 24, 2012, 7:22:28 AM5/24/12
to salt-...@googlegroups.com
Hi,

I try to untar some file inside my module. So I do:

os.chdir("<targz_location>")
__salt__['archive.tar']("zxf", "<targz_file_name")

When I do that it doesn't change cwd with os.chdir command. Any ideas why?
Thanks, Alex A. 

On Sunday, May 13, 2012 6:39:56 PM UTC+3, Thomas Hatch wrote:

Thomas S Hatch

unread,
May 26, 2012, 3:53:43 PM5/26/12
to salt-...@googlegroups.com
Thats odd, does
os.getcwd()
return a changed directory? Or could it be a path issue when calling the tar command?

Alex Arshavski

unread,
Jun 4, 2012, 10:03:15 AM6/4/12
to salt-...@googlegroups.com
Hi,

os.getcwd() return the changed directory. But it doesn't actually change for some reason.

Regards, Alex A.

Alex Arshavski

unread,
Jun 18, 2012, 6:13:27 AM6/18/12
to salt-...@googlegroups.com
Hi,

I have wrote the following module:

def test():
    log="1: %s\n" % os.getcwd()
    os.chdir("/home")
    log+="2: %s\n" % os.getcwd()
    __salt__['cmd.run']('cd /tmp')
    log+="3: %s\n" % os.getcwd()
    log+="4: %s" % __salt__['cmd.run']('pwd')
    return log

Running the module gives me the following result:

ip-XX-XX-XX-XX.ec2.internal: 1: /tmp
ip-XX-XX-XX-XX.ec2.internal: 2: /home
ip-XX-XX-XX-XX.ec2.internal: 3: /home
ip-XX-XX-XX-XX.ec2.internal: 4: /home/rad

And I would expect to get "/home" also in step 4.

Is it a bug or I'm doing something wrong?

Regards, Alex.

Thomas S Hatch

unread,
Jun 18, 2012, 10:14:51 AM6/18/12
to salt-...@googlegroups.com
Oh, if you are shelling out then use the "cwd" argument to cmd.run:

def test():
    log="1: %s\n" % os.getcwd()
    os.chdir("/home")
    log+="2: %s\n" % os.getcwd()
    __salt__['cmd.run']('cd /tmp', cwd="/home")
    log+="3: %s\n" % os.getcwd()
    log+="4: %s" % __salt__['cmd.run']('pwd', cwd="/tmp")
    return log

And you don't need to execute os.chdir, I don't think that I realized that you were running cmd.run.

Alex Arshavski

unread,
Jun 19, 2012, 3:35:08 AM6/19/12
to salt-...@googlegroups.com
Yes. but what if I need to run multiple commands in some directory? For example, if I compile something, I have to run:

__salt__['cmd.run']('configure;make;make install', cwd="<my_dir>")

Is there a way to split it, so I could change cwd and next __salt__['cmd.run'] call will remember it?

Regards, Alex A.

Thomas S Hatch

unread,
Jun 19, 2012, 11:45:06 AM6/19/12
to salt-...@googlegroups.com
Not right now, no. Feel free to open an issue. I don't quite know how to do it cleanly yet though, so no promises :)

Jeff Hutchins

unread,
Jun 20, 2012, 9:20:01 AM6/20/12
to salt-...@googlegroups.com
Alex, would you be opposed to just doing something like the following in your module?

for cmd in ['configure', make', 'make install']:
__salt__['cmd.run'](cmd, cwd="<my_dir>")

Or maybe Thomas wants to make it so if you pass in a list or tuple of commands to cmd.run it does this. I would be more than willing to make this change.

Thomas S Hatch

unread,
Jun 20, 2012, 11:05:48 AM6/20/12
to salt-...@googlegroups.com
Good call Jeff, I think that having the ability to pass a list of commands into cmd functions would be killer

Jeff Schroeder

unread,
Jun 20, 2012, 6:10:00 PM6/20/12
to salt-...@googlegroups.com, salt-...@googlegroups.com

Text by Jeff, typos by iPhone
The other jeff here...

Perhaps a "names" argument to match some of the other modules? Or "cmds"?

__salt__['cmd.run'](names=['ls', 'whoami', 'pwd'], cwd='/var/lib')

Jeff Hutchins

unread,
Jun 21, 2012, 11:38:49 AM6/21/12
to salt-...@googlegroups.com
If we're going to go that way I would probably lean towards cmds over names, but really it would be up to our benevolent salt dictator (Thomas Hatch).

Thomas S Hatch

unread,
Jun 21, 2012, 12:33:07 PM6/21/12
to salt-...@googlegroups.com
Please don't make it names, names is a special argument value that is recognized by the salt state compiler.

I honestly think that what we should do is check to see if cmd is a list object, and then iterate over it if it is

Les Mikesell

unread,
Jun 21, 2012, 4:06:49 PM6/21/12
to salt-...@googlegroups.com
On Thu, Jun 21, 2012 at 11:33 AM, Thomas S Hatch <that...@gmail.com> wrote:
> Please don't make it names, names is a special argument value that
> is recognized by the salt state compiler.
>
> I honestly think that what we should do is check to see if cmd is a list
> object, and then iterate over it if it is

In the list case, would all cmds be executed in the same shell process?

--
Les Mikesell
lesmi...@gmail.com

Thomas S Hatch

unread,
Jun 21, 2012, 4:09:45 PM6/21/12
to salt-...@googlegroups.com
That's a technical point that I am not sure of yet, I would think that there would be separate shell calls for each command 

Les Mikesell

unread,
Jun 21, 2012, 4:47:09 PM6/21/12
to salt-...@googlegroups.com
On Thu, Jun 21, 2012 at 3:09 PM, Thomas S Hatch <that...@gmail.com> wrote:
>
>
>> >
>> > I honestly think that what we should do is check to see if cmd is a list
>> > object, and then iterate over it if it is
>>
>> In the list case, would all cmds be executed in the same shell process?
>>
> That's a technical point that I am not sure of yet, I would think that there
> would be separate shell calls for each command

Either way there will probably be some subtle surprises. Is there a
way to construct a shell script on the fly with variable substitution
and execute it without worrying about a temporary file copy?

--
Les Mikesell
lesmi...@gmail.com

Thomas S Hatch

unread,
Jun 21, 2012, 7:42:44 PM6/21/12
to salt-...@googlegroups.com
Yes, there is, I am leaning a little more in that direction here.

Sean Channel

unread,
Jun 21, 2012, 7:58:27 PM6/21/12
to salt-...@googlegroups.com
Building a script would ensure the whole batch is run with the same environment, which is certainly the expectation for shell scripts.

Perhaps if 'cmd' is a list it can become a shell script?
_s

Sean Channel

unread,
Jun 21, 2012, 8:17:07 PM6/21/12
to salt-...@googlegroups.com
Or you could just separate each command in the llist with a semi-colon and feed it all as one long string to a single "sh -c"

- no temporary files created
- all in same environment


_s

On 06/21/2012 04:42 PM, Thomas S Hatch wrote:

Jeff Hutchins

unread,
Jun 22, 2012, 10:10:22 AM6/22/12
to salt-...@googlegroups.com
That begs the question, what do you gain from using a list of commands instead of just passing one string that's a bunch of commands separated by semicolons?

Les Mikesell

unread,
Jun 22, 2012, 10:56:31 AM6/22/12
to salt-...@googlegroups.com
On Fri, Jun 22, 2012 at 9:10 AM, Jeff Hutchins <comp...@gmail.com> wrote:
> That begs the question, what do you gain from using a list of commands instead of just passing one string that's a bunch of
commands separated by semicolons?

And will either of those get loop structures with i/o redirection for
the loop right?

--
Les Mikesell
lesmi...@gmail.com

Thomas S Hatch

unread,
Jun 22, 2012, 11:00:27 AM6/22/12
to salt-...@googlegroups.com
I am now leaning more towards something like this:
where the publish itself can either just contain a script (which can be done now with cmd.exec_code) or the command can accept a script location to download and run. any multi command execution can be done with a series of semicolon delimited commands

Les Mikesell

unread,
Jun 22, 2012, 1:55:51 PM6/22/12
to salt-...@googlegroups.com
On Fri, Jun 22, 2012 at 10:00 AM, Thomas S Hatch <that...@gmail.com> wrote:
> I am now leaning more towards something like this:
> https://github.com/saltstack/salt/issues/1486
> where the publish itself can either just contain a script (which can be done
> now with cmd.exec_code) or the command can accept a script location to
> download and run. any multi command execution can be done with a series of
> semicolon delimited commands

So why not go all the way and make shell (and maybe some other
languages) a full alternative to python for components? In any case
it needs a way to substitute variables on the fly without conflicting
with shell's own concepts or escaping mechanisms.

--
Les Mikesell
lesmi...@gmail.com

Thomas S Hatch

unread,
Jun 22, 2012, 1:59:36 PM6/22/12
to salt-...@googlegroups.com
Yes, I have been debating about how to do this for a while. Obviously we would not accept non-python/C modules upstream, but building a generic hook for this would be nice. I acctually have an issue open from more than a year ago on this, I just have not seen enough demand to dedicate the time for it

Les Mikesell

unread,
Jun 22, 2012, 2:31:06 PM6/22/12
to salt-...@googlegroups.com
On Fri, Jun 22, 2012 at 12:59 PM, Thomas S Hatch <that...@gmail.com> wrote:
>
>>
>> So why not go all the way and make shell (and maybe some other
>> languages) a full alternative to python for components?  In any case
>> it needs a way to substitute variables on the fly without conflicting
>> with shell's own concepts or escaping mechanisms.
>>
>
> Yes, I have been debating about how to do this for a while. Obviously we
> would not accept non-python/C modules upstream, but building a generic hook
> for this would be nice. I acctually have an issue open from more than a year
> ago on this, I just have not seen enough demand to dedicate the time for it

I'm not sure I'd want the resource consumption of a jvm running all
the time on the minions (but then again, what does that really cost
these days when even cell phones do it?) but off the top of my head I
think I'd like to see groovy as the language of choice. It has a
nice syntax for scripting and inherits not only portability from java
but the ability to use any compiled java jars directly. Anyway it
works great in jenkins (which can even auto-install it on the slaves)
when targeting multiple platforms...

--
Les Mikesell
lesmi...@gmail.com

Thomas S Hatch

unread,
Jun 22, 2012, 5:11:56 PM6/22/12
to salt-...@googlegroups.com
Yes, the thing to do here is to create a generic bridge so that we can have bridges to other languages easily added, then Salt would be able to execute modules from any language, even groovy :) 

Les Mikesell

unread,
Jun 22, 2012, 5:31:58 PM6/22/12
to salt-...@googlegroups.com
On Fri, Jun 22, 2012 at 4:11 PM, Thomas S Hatch <that...@gmail.com> wrote:
>
>> I'm not sure I'd want the resource consumption of a jvm running all
>> the time on the minions (but then again, what does that really cost
>> these days when even cell phones do it?) but off the top of my head I
>> think I'd like to see groovy as the language of choice.   It has a
>> nice syntax for scripting and inherits not only portability from java
>> but the ability to use any compiled java jars directly.  Anyway it
>> works great in jenkins (which can even auto-install it on the slaves)
>> when targeting multiple platforms...
>>
> Yes, the thing to do here is to create a generic bridge so that we can have
> bridges to other languages easily added, then Salt would be able to execute
> modules from any language, even groovy :)

Maybe jython would do the same thing without drastic code changes (or
having to deal with getting python installed on windows....). But, I
got the impression somewhere that you planned a wire-level protocol
spec that would let minions run completely different languages. I
suppose python is a special-case language for administering linux
since yum, etc. are going to already need it in the distributions, but
it isn't universal across platforms.

--
Les Mikesell
lesmi...@gmail.com

Thomas S Hatch

unread,
Jun 22, 2012, 5:35:32 PM6/22/12
to salt-...@googlegroups.com
Yes, Salt does not need to have the minion side run python at all, eventually I want to write minions for other devices where python makes less sense, but that is a little ways down the road :)

Alex Arshavski

unread,
Jul 5, 2012, 2:31:06 AM7/5/12
to salt-...@googlegroups.com
Thomas,

And what can I do in this command:  __salt__['archive.tar']("zxf", "/usr/local/src/some_archive.tar.gz")
How can I tell salt where I want this archive to be opened to?

Thanks, Alex A.

Sean Channel

unread,
Jul 5, 2012, 11:30:44 AM7/5/12
to salt-...@googlegroups.com

On 07/04/2012 11:31 PM, Alex Arshavski wrote:
> And what can I do in this command: __salt__['archive.tar']("zxf",
> "/usr/local/src/some_archive.tar.gz")
> How can I tell salt where I want this archive to be opened to?

tar has a '-C' option for this to tell it where to 'chdir' to.

_S

Les Mikesell

unread,
Jul 5, 2012, 11:37:34 AM7/5/12
to salt-...@googlegroups.com
I think that is a Gnu tar extension. Might not work on systems that
don't use the gnu flavor - if there are any these days.

--
Les Mikesell
lesmi...@gmail.com

Alex Arshavski

unread,
Jul 8, 2012, 4:21:14 AM7/8/12
to salt-...@googlegroups.com
Thanks for the reply.
Can you tell exactly where should I add the "-C" option in __salt__['archive.tar']("zxf", "<targz_file_name") ?

Thanks, Alex A.

Devon Stewart

unread,
Jul 8, 2012, 5:05:20 AM7/8/12
to salt-...@googlegroups.com
Based on the source, looks like ("xzC /foo/bar -f", ...)

That being said, that looks horrible. A-C flag should probably be added to the module.

-Devon

Alex Arshavski

unread,
Jul 8, 2012, 8:25:42 AM7/8/12
to salt-...@googlegroups.com
Nope, It doesn't work with "-C" option. Is there another way?

Thanks, Alex A.

Devon Stewart

unread,
Jul 8, 2012, 3:01:12 PM7/8/12
to salt-...@googlegroups.com
What was the call you used?

-Devon

Alex Arshavski

unread,
Jul 8, 2012, 3:22:11 PM7/8/12
to salt-...@googlegroups.com
__salt__['archive.tar']("zxC /usr/local/src -f", "/usr/local/src/libevent-1.4.14b-stable.tar.gz")

Ella Megalast

unread,
Jul 9, 2012, 3:20:36 PM7/9/12
to salt-...@googlegroups.com
any shell command can have an embedded 'cd' by grouping w/ parentheses;

$ (cd /source/dir/; tar -cf - .) | (cd /target/dir/; tar -xvf -)

fwiw.
_s

Alex Arshavski

unread,
Jul 10, 2012, 4:44:05 AM7/10/12
to salt-...@googlegroups.com
Yes, I know. I just wanted to use __salt__['archive.tar'] and it's pretty strange that I don't have an option to say to archive module where to extract to.

Regards, Alex A.
Reply all
Reply to author
Forward
0 new messages