2015-11-11 2 views
3

У меня есть определенные ограничения, которые я не буду указывать, которые требуют от меня использовать ImageMagick в качестве дочернего процесса.Передача 2 аргументов stdin в ImageMagick child_process

У меня есть несколько базовых 64 строк jpg-файлов, которые я хочу обработать ImageMagick. В частности, я хочу, чтобы ImageMagick присоединился к файлам jpg вместе. Если бы у меня было 2 обычных файла jpg, то из командной строки я использовал бы следующий формат.

node convert in_1.jpg in_2.jpg +append out.jpg 

в файле JS Я хотел бы использовать

var spawn, magicCommands, imagic; 
spawn = require('child_process').spawn; 
magicCommands = ["in_1.jpg", 
       "in_2.jpg", 
       "+append", 
       "out.jpg"]; 
imagic = spawn("convert", magicCommands); 

Теперь, если я хотел использовать STDIN буфер следующий будет работать

var arrow1JpgBase64, arrow2JpgBase64, arrowBuffer1, arrowBuffer2, magicCommands, imagic; 

    spawn = require('child_process').spawn; 
    exec = require('child_process').exec; 

    arrow1JpgBase64 = "/9j/4AAQSkZJRgABAQEAYABgAAD/2wBDAAUDBAQEAwUEBAQFBQUGBwwIBwcHBw8LCwkMEQ8SEhEPERETFhwXExQaFRERGCEYGh0dHx8fExciJCIeJBweHx7/2wBDAQUFBQcGBw4ICA4eFBEUHh4eHh4eHh4eHh4eHh4eHh4eHh4eHh4eHh4eHh4eHh4eHh4eHh4eHh4eHh4eHh4eHh7/wAARCAAFAAkDASIAAhEBAxEB/8QAHwAAAQUBAQEBAQEAAAAAAAAAAAECAwQFBgcICQoL/8QAtRAAAgEDAwIEAwUFBAQAAAF9AQIDAAQRBRIhMUEGE1FhByJxFDKBkaEII0KxwRVS0fAkM2JyggkKFhcYGRolJicoKSo0NTY3ODk6Q0RFRkdISUpTVFVWV1hZWmNkZWZnaGlqc3R1dnd4eXqDhIWGh4iJipKTlJWWl5iZmqKjpKWmp6ipqrKztLW2t7i5usLDxMXGx8jJytLT1NXW19jZ2uHi4+Tl5ufo6erx8vP09fb3+Pn6/8QAHwEAAwEBAQEBAQEBAQAAAAAAAAECAwQFBgcICQoL/8QAtREAAgECBAQDBAcFBAQAAQJ3AAECAxEEBSExBhJBUQdhcRMiMoEIFEKRobHBCSMzUvAVYnLRChYkNOEl8RcYGRomJygpKjU2Nzg5OkNERUZHSElKU1RVVldYWVpjZGVmZ2hpanN0dXZ3eHl6goOEhYaHiImKkpOUlZaXmJmaoqOkpaanqKmqsrO0tba3uLm6wsPExcbHyMnK0tPU1dbX2Nna4uPk5ebn6Onq8vP09fb3+Pn6/9oADAMBAAIRAxEAPwD1/wCFngjxJba78QbWT4reLTLH4pZ2mjt9PLTCSxs5VL+bbSYZUkWPCFUxGu1EHFdz/wAIb4j/AOiseM//AAF0n/5BoooA/9k="; 
    arrow2JpgBase64 = "/9j/4AAQSkZJRgABAQEAYABgAAD/2wBDAAUDBAQEAwUEBAQFBQUGBwwIBwcHBw8LCwkMEQ8SEhEPERETFhwXExQaFRERGCEYGh0dHx8fExciJCIeJBweHx7/2wBDAQUFBQcGBw4ICA4eFBEUHh4eHh4eHh4eHh4eHh4eHh4eHh4eHh4eHh4eHh4eHh4eHh4eHh4eHh4eHh4eHh4eHh7/wAARCAAFAAkDASIAAhEBAxEB/8QAHwAAAQUBAQEBAQEAAAAAAAAAAAECAwQFBgcICQoL/8QAtRAAAgEDAwIEAwUFBAQAAAF9AQIDAAQRBRIhMUEGE1FhByJxFDKBkaEII0KxwRVS0fAkM2JyggkKFhcYGRolJicoKSo0NTY3ODk6Q0RFRkdISUpTVFVWV1hZWmNkZWZnaGlqc3R1dnd4eXqDhIWGh4iJipKTlJWWl5iZmqKjpKWmp6ipqrKztLW2t7i5usLDxMXGx8jJytLT1NXW19jZ2uHi4+Tl5ufo6erx8vP09fb3+Pn6/8QAHwEAAwEBAQEBAQEBAQAAAAAAAAECAwQFBgcICQoL/8QAtREAAgECBAQDBAcFBAQAAQJ3AAECAxEEBSExBhJBUQdhcRMiMoEIFEKRobHBCSMzUvAVYnLRChYkNOEl8RcYGRomJygpKjU2Nzg5OkNERUZHSElKU1RVVldYWVpjZGVmZ2hpanN0dXZ3eHl6goOEhYaHiImKkpOUlZaXmJmaoqOkpaanqKmqsrO0tba3uLm6wsPExcbHyMnK0tPU1dbX2Nna4uPk5ebn6Onq8vP09fb3+Pn6/9oADAMBAAIRAxEAPwD1/wCOvgjxJc/Dt7NPit4tMt1q+k20Ty2+nqsLyajbIkoMFtFJuRmDjbIpyo5xmu5/4Q3xH/0Vjxn/AOAuk/8AyDRRQB//2Q=="; 
    arrowBuffer1 = new Buffer(arrow1JpgBase64, 'base64'); 
    arrowBuffer2 = new Buffer(arrow2JpgBase64, 'base64'); 
    magicCommands = ["jpg:", 
        "in_2.jpg", 
        "+append", 
        "out.jpg"]; 

    imagic = spawn("convert", magicCommands); 
    imagic.stdin.write(arrowBuffer1); 
    imagic.stdin.end(); 

    imagic.on('exit', function (code) { 
     if (code === 0) { 
      exec("open out.jpg"); 
     } else { 
      console.log("error code: " + code); 
     } 
    }); // end of on exit 

До сих пор так хорошо, но я хотите использовать как буферов, а не только из них. Поэтому, если я заменил строку "in_2.jpg", на "jpg:",, то как мне изменить оставшуюся часть скрипта, чтобы заставить его работать?

Благодаря

+1

Gotta тиру, но, возможно, вы можете использовать 'ФД:' обработчик в ImageMagick и поместил один буфер на 'fd: 3', а другой на' fd: 4' ... http://www.imagemagick.org/Usage/files/#fd –

+0

Если у вас уже есть base64 строка (и это <5000 символов), иначе [передать это как аргумент напрямую] (http://www.imagemagick.org/Usage/files/# inline) w/'inline: data: image/jpeg; base64, ...'? – emcconville

+0

@emcconville Я пытался сделать то же самое сам, но, похоже, он больше не работает, я попробовал пример Курта здесь ... http://stackoverflow.com/a/12067952/2836621 и пример под ** ASIDE * * здесь ... http://www.imagemagick.org/Usage/files/#inline Все это кажется нарушенным в IM v6.9.2-5. –

ответ

1

Не совсем уверен, что эти «ограничения» являются, или то, что мы пытаемся избежать или обойти, но следующий метод потоковой передачи нескольких файлов в один может помочь вам:

# Make a red block 
convert -size 50x50 xc:red multi.miff 

# Make a green block, but APPEND INTO A SINGLE STREAM 
convert -size 50x50 xc:lime miff:- >> multi.miff 

# Make a blue block, but APPEND INTO A SINGLE STREAM 
convert -size 50x50 xc:blue miff:- >> multi.miff 

# Tell IM to convert and append multiple images in single stream 
convert multi.miff +append result.png 

enter image description here

Кроме того, если вы измените последнюю команду выше следующему, IM удалит файл multi.miff, как только он закончил с ним - то есть убирайся за тобой!

convert ephemeral:multi.miff +append result.png 
+0

Еще раз спасибо ограничениям, которые я имел в виду, это то, что я не могу использовать собственные модули узла на основе C++, поэтому исключаю использование lwip или других возможных вариантов. Я действительно ищу, чтобы избежать ненужной записи на жесткий диск. Буферы уже существуют, поэтому, если бы я мог просто передать их в качестве аргументов, было бы лучше сохранить их в виде файлов, а затем удалить файлы впоследствии. Я отправлю еще один шаг о получении fd буфера, если есть такая вещь! – Trevor

+1

Хорошо, я приближаюсь к пониманию, я думаю ... вы считали небольшой RAMdisk для временных файлов? –

+0

Нет, это для системы клиентов, для нескольких установок. Возможно, я просто прибегну к созданию и стиранию файла. Но я сначала займусь созданием потоков буфера, и я думаю, что они могут быть упомянуты их fd, которые, как мне кажется, у них есть. Я разместил сообщение здесь http://www.imagemagick.org/discourse-server/viewtopic.php?t=13100, но не понял ответа – Trevor

3

Как Марк Setchell отметил в комментариях, используя протокол ImageMagick в fd: будет работать.

var spawnOptions = { 
     stdio: [ 
     0, // stdin, 
     1, // stdout 
     2, // stderr 
     'pipe', // arrowBuffer1 
     'pipe' // arrowBuffer2 
     ] 
}; 
magic = spawn("convert", magicCommands, spawnOptions); 

Это открывает fd:3 & fd:4 для трубопроводов. Я не сбой с семейством , но обычно есть способ передать ресурс в дополнение к .

Для кода

Update переменной magickCommands для чтения из новых fd-й лет, и писать непосредственно к новому pipes

magicCommands = ["fd:3", 
       "fd:4", 
       "+append", 
       "out.jpg"]; 

// ... 
imagic.stdio[3].write(arrowBuffer1); 
imagic.stdio[4].write(arrowBuffer2); 
imagic.stdio[3].end(); 
imagic.stdio[4].end(); 
+0

Я получаю сообщение, что imagic.stdio [3] не определено, и я не могу писать на него. Я думаю, хотя это приближается – Trevor

Смежные вопросы