8

I have been struggling for a while with this one. So I wrote a .specs file for my project and everything went fine. The rpm is built, the installation is smooth... but then I got some trouble because now, I have to use a custom global environment variable to set the install path.

This would give a %files section as such :

%files
%defattr(-,root,root)
$INSTALLPATH/Crystal/bin/Crystal.jar

Where Crystal is my project name, and INSTALLPATH is defined within env thanks to the export commandline. Then, when running buildrpm -ba Crystal.specs I have the following error:

error: File must begin with "/" : $INSTALLPATH/Crystal/bin/Crystal.jar

I have tried to define a macro inside the .rpmmacros file as such : %_installpath $INSTALLPATH

And in my specs file, when i do echo %{_installpath} I get the value I set in the .rpmmacros. But if I use it in %files:

%files
%defattr(-,root,root)
%{_installpath}/Crystal/bin/Crystal.jar

I get the same error again!

error: File must begin with "/" : $INSTALLPATH/Crystal/bin/Crystal.jar

I also tried defining a variable with the specs file and I have the same sad result. It looks like as long as my variable/macro is referencing to $INSTALL, then %files won't accept it. But I have to use this env variable!

So that's all I could think about. Anyone got a clue? Any help would be greatly appreciated.

Thanks a lot in advance!

Rinita
  • 147
  • 1
  • 1
  • 9

1 Answers1

8

The %files section does not expand shell variables. You cannot do this that way.

You have a couple options that I can see offhand. You can

  • generate a file with a list of your files (during %install or what-have-you) and then use %files -f files.lst

  • expand $INSTALLPATH at rpm macro definition time with:

    # For RPM >= 4.7.0
    %_installpath %{getenv:INSTALLPATH}
    # For RPM < 4.7.0
    %_installpath %{lua:print(os.getenv("INSTALLPATH"))}
    
Etan Reisner
  • 77,877
  • 8
  • 106
  • 148
  • Yes, that was it. I used the first solution. Thanks a lot! – Rinita Sep 18 '14 at 07:32
  • @Etan Reisner: You can use shell variables in `%files` section the same way as anywhere else in the spec, although that might be pretty ugly and unreadable. E.g. using `%(echo $INSTALLPATH/Crystal/bin/Crystal.jar)` should achieve what the OP wanted. – doktor5000 Dec 30 '15 at 16:15
  • @doktor5000 That's not the `%files` section expanding shell variables though (and I don't believe the `%files` section does that). That's `rpm` doing the expansion at parse time manually because you used the `%(...)` macro. But yes, that would (possibly) have worked... assuming `%(...)` expansions are performed in the right macro scope. – Etan Reisner Dec 30 '15 at 16:18
  • @EtanReisner: Definitely works in `%files` section, we use it for some particularly ugly packages to tag certain files dynamically with `%lang($lang)` and basically create that part of the `%files` section on the fly. But your proposed solution with the files list is probably much cleaner for the OP :) – doktor5000 Dec 31 '15 at 03:12
  • @doktor5000 What specifically works in the `%files` section? An entry like `/usr/lib/$shellvar`? Your dynamically created file list contains `%lang($lang) /path/to/file` in it? Or does it contain `%lang(en) /path/to/file`? – Etan Reisner Dec 31 '15 at 04:27
  • @EtanReisner: This is basically what I use in `%files` `%(for lang in %langs ; do echo "%%lang($lang) /path/to/file-$lang" done)` where `%langs` is a list of locales. – doktor5000 Dec 31 '15 at 16:37
  • @doktor5000 Yes, that's an *explicit* invocation of the shell with a variable being defined in *that* shell script (as that's a shell for loop). That's not at all the same as the `%files` section expanding shell variables in normal usage. Try using a shell variable from your `%build` or `%install` sections in that loop or just using the variable in the `%files` list directly and you'll see what I mean about it not working. – Etan Reisner Jan 01 '16 at 19:55