How do I have premake run an external tool only if the target is out of date - premake

As part of my build process, I have an archive that I need to extract. I can use prebuildcommands to always extract it, but that is repetitive and will slow the build.
How do say "run this command only if the extracted directory does not exist".
It would be good to also extract the file if the archive is new than the directory, but I'm less concerned about that, as I do not expect the archive to change often.
Edit: I have an external requirement to use Premake 4.

It looks like the documentation is a little incomplete, but (using Premake5) maybe something like this?
buildcommands { "cmd to unarchive the file" }
buildinputs { "name of archive" }
buildoutputs { "name of a file from the archive" }

Related

Flow-typed - Generate Libdef

I'm using Flow to help author a JS project. If I want to provide a libdef file to supplement it do I need to create it manually, or am I able to execute some magic command that I'm not aware of yet which will generate the lib def for me?
Something like $ flow-typed doyourmagic would be nice.
EDIT:
Found this https://stackoverflow.com/a/38906578/192999
Which says:
There's two things:
If the file is owned by you (i.e. not a third party lib inside node_modules or such), then you can create a *.js.flow file next to it that documents its exports.
If the file is not owned by you (i.e. third party lib inside node_modules or such), then you can create a libdef file inside flow-typed/name-of-library.js
For .js.flow files
you write the definitions like this:
// #flow
declare module.exports: { ... }
For libdef files you write the definitions like this:
declare module "my-third-party-library" { declare module.exports: {... } }
For my question I fall into the "is owned by you" camp.
I guess I'm confused as to:
How I write these files.
How/where I publish these files to package it up for another project to reference.
Also, why do I need to create the .js.flow file manually? Can this not be magically generated? Perhaps that's the intention going forward but not implemented yet.
I found a nice guide showing how to package flow code together with the compiled code. So:
You do not have to write your own libdefs, you can use the entire flow source code. If you want a definition with only the type declarations, you can look into flow gen-flow-files, although that is still experimental and might fail.
You can package them as *.js.flow and the flow checker will automatically pick those up when you import your library.

Grunt-init copyAndProcess function: Can I pass in multiple values to 'noProcess' option?

I'm using grunt-init to build a template for a site structure I repeat regularly.
The template.js file uses the init.copyAndProcess function to customize most of files but a few of them get corrupted by the file processing (some fonts and image files) and I want to include those files in the 'noProcess' option. If these files all existed in the same directory, I could use the noProcess option as mentioned in the documentation [ See: http://gruntjs.com/project-scaffolding#copying-files ] and pass in a string like and it works:
var files = init.filesToCopy(props);
init.copyAndProcess(files, props, {noProcess: 'app/fonts/**'} );
Unfortunately the files that I need to have no processing performed on are not all in the same directory and I'd like to be able to pass in an array of them, something like the following block of code, but this does not work.
var files = init.filesToCopy(props);
init.copyAndProcess(files, props, {noProcess: ['app/fonts/**', 'app/images/*.png', 'app/images/*.jpg']} );
Any thoughts on how I can have multiple targets for the 'noProcess' option?
As soon as I posted the question, I realized that my proposed code did work. I simply had an invalid path when I'd renamed my 'app' directory to 'dev'.

Qt Installer framework component installation location

I've created an installer package based on the Qt installer framework with multiple components.
I needed to install each component in the appropriate directory.
Is it possible to specify the target directory for the individual component? I am referring to something like this:
var appData = installer.environmentVariable("AppData");
if (appData != "")
component.setValue("TargetDir", appData+ "/MyComponent");
Thank you in advance.
This question has already been answered, but I thought I would add a more detailed answer.
The documentation states that "for each component, you can specify one script that prepares the operations to be performed by the installer."
The Qt installer framework QtIFW comes with a set of examples, one of which is called modifyextract. Using this, I modified my package.xml file to include the line
<Script>installscript.qs</Script>
I then added a file installscript.qs to my package meta directory with the following content
function Component()
{
}
Component.prototype.createOperationsForArchive = function(archive)
{
// don't use the default operation
// component.createOperationsForArchive(archive);
// add an extract operation with a modified path
component.addOperation("Extract", archive, "#TargetDir#/SubDirectoryName");
}
The files in the package data folder were then installed in the subfolder SubDirectoryName
You need this based on the documentation:
Extract "Extract" archive target directory Extracts archive to target directory.
In my case, the component.addOperation("Extract", ... line resulted in extracting to #TargetDir#.
Instead, use one of the 'Operations> options in the Package.xml file.

autohotkey wildcard read loop

I want one script to command several computers to break up a highly distributable workload. In order to distribute the workload I put half of the task labels in one file, and half of the tasks in another file that i distribute to the computers with google drive (which is why i need different file names). So C:\googledrive\task1.txt and C:\googledrive\task2.txt
The autohotkey command looks like:
loop, read, c:\googledrive\task*.txt
But instead of reading task1.txt, it appears to try to read "task*.txt" as a literal file name, fails, and ends the loop.
Ideas? Thanks.
OK, tried ensuring everything was running with administrator rights (they are) and ensured that the files exist (they do) and no typos in the file path (everything good there). Still wont actually read the file.
There is one bit that I didn't include in the original post part of the file name is actually a variable, so the loop command is actually like:
loop, read, c:\googledrive\%task%*.txt
I just figured that bit was inconsequential.
If i save a different script for each computer, i can go ahead and replace the wildcard with the actual bit, and it works.
so... Im just going to name each file with the computer's name in the file, and change the command to:
loop, read, c:\googledrive\%task%%A_ComputerName%.txt
I do it this way....
Loop, C:\Temp\Source\*.txt ; Lists the next file as A_LoopFileName
{
Loop, read, C:\Temp\Source\%A_LoopFileName% ; process current file
{
IfInString, A_LoopReadLine, abc
{
.......
}
}
}

How to work with hook_nodeapi after image thumbnail creation with ImageCache

A bit of a followup from a previous question.
As I mentioned in that question, my overall goal is to call a Ruby script after ImageCache does its magic with generating thumbnails and whatnot.
Sebi's suggestion from this question involved using hook_nodeapi.
Sadly, my Drupal knowledge of creating modules and/or hacking into existing modules is pretty limited.
So, for this question:
Should I create my own module or attempt to modify the ImageCache module?
How do I go about getting the generated thumbnail path (from ImageCache) to pass into my Ruby script?
edit
I found this question searching through SO...
Is it possible to do something similar in the _imagecache_cache function that would do what I want?
ie
function _imagecache_cache($presetname, $path) {
...
...
// check if deriv exists... (file was created between apaches request handler and reaching this code)
// otherwise try to create the derivative.
if (file_exists($dst) || imagecache_build_derivative($preset['actions'], $src, $dst)) {
imagecache_transfer($dst);
// call ruby script here
call('MY RUBY SCRIPT');
}
Don't hack into imagecache, remember every time you hack core/contrib modules god kills a kitten ;)
You should create a module that invokes hook_nodeapi, look at the api documentation to find the correct entry point for your script, nodeapi works on various different levels of the node process so you have to pick the correct one for you (it should become clear when you check the link out) http://api.drupal.org/api/function/hook_nodeapi
You won't be able to call the function you've shown because it is private so you'll have to find another route.
You could try and build the path up manually, you should be able to pull out the filename of the uploaded file and then append it to the directory structure, ugly but it should work. e.g.
If the uploaded file is called test123.jpg then it should be in /files/imagecache/thumbnails/test123/jpg (or something similar).
Hope it helps.

Resources