Posixy способ запустить браузер?

Есть ли способ «Posixy» открыть URL-адрес, предпочтительно в браузере по умолчанию? Я хотел бы сделать что-то вроде

ShellExecute(0, _T("open"), url, 0, 0, SW_SHOWDEFAULT);

который работает на GNU/Linux и MAC. Я прочитал какой-то ответ, в котором говорилось, что`

if (fork() == 0)
    system("sensible-browser http://wherever.com");

по крайней мере, помогает в системах Debian. Есть ли простой способ распространить это на то, что работает в других дистрибутивах и Mac OS X?


person Jonas Byström    schedule 23.12.2009    source источник
comment
Я беру свои слова обратно насчет дубликата. Связанная ссылка: stackoverflow.com/questions/1949531/   -  person dmckee --- ex-moderator kitten    schedule 23.12.2009
comment
Я бы не стал полагаться на поддержку Posix в MacOSX для таких вещей, потому что это может противоречить ожиданиям пользователей.   -  person Georg Fritzsche    schedule 23.12.2009


Ответы (5)


На Mac вы можете просто использовать команду open. open http://www.google.com из Терминала открывает для меня новую вкладку Chrome. Просто оберните это вызовом system.

person eduffy    schedule 23.12.2009

В Linux вы должны попробовать запустить свой URL-адрес с помощью команды xdg-open. Более новые дистрибутивы должны запускать предпочитаемый пользователем браузер при вызове этой команды. Он даже попытается запустить ссылки, если не запущен графический интерфейс.

Очевидно, что в POSIX нет ничего относительно среды рабочего стола с графическим интерфейсом. Такие проекты, как freedesktop.org, существуют для выполнения этой роли. Он пытается определить некоторые базовые функции, которые будут работать на всех Unix-подобных рабочих столах, таких как GNOME и KDE.

Выполнение fork() и вызов system() вместо exec() является неопределённым поведением в POSIX, поэтому я этого не рекомендую.

person karunski    schedule 23.12.2009
comment
Значит, system() определена только для родительских процессов? Я не говорю, что вы ошибаетесь, но я не понимаю, почему, поскольку разветвленный процесс имеет свое собственное адресное пространство и все такое. Для меня это все равно, что сказать, что вы не можете использовать printf() после разветвления. - person SiegeX; 23.12.2009
comment
Я также не понимаю, почему system() является неопределенным поведением в POSIX после fork(), можете ли вы процитировать соответствующую часть стандарта POSIX? Спасибо. - person Chris Young; 23.12.2009
comment
За fork() должен следовать exec(). Между ними вы можете вызывать только безопасные для асинхронного сигнала функции. System() не гарантирует безопасность асинхронного сигнала, как и printf. - person karunski; 23.12.2009
comment
Вызов system() после форка не имеет смысла. Вы можете сделать fork, exec, а затем system(), но тогда это будет избыточно. - person karunski; 23.12.2009
comment
Из руководства fork(): Когда программист пишет многопоточную программу, первое описанное использование fork(), создание новых потоков в той же программе, обеспечивается функцией pthread_create(). Таким образом, функция fork() используется только для запуска новых программ, а эффекты вызова функций, требующих определенных ресурсов, между вызовом fork() и вызовом функции exec не определены. - person karunski; 23.12.2009
comment
Однако я считаю, что это верно только для многопоточных программ. - person ephemient; 23.12.2009
comment
Строго говоря, да, ограничение распространяется только на многопоточные программы. Но на практике другой код ОС, такой как библиотека C или любой другой фреймворк, может неявно создавать потоки. Обратите внимание, что руководство для fork() в OS X не делает различий для многопоточных программ. - person karunski; 23.12.2009

Предпочтения пользователя в браузере на самом деле не относятся к стандарту POSIX, о чем я знаю.

person Azeem.Butt    schedule 23.12.2009

Одним из способов может быть переменная $BROWSER. Xorg предоставляет xrdb, который является предпочтительным способом для этой среды, но я полагаю, что это не даст вам ничего в Mac OS X.

person pmr    schedule 23.12.2009

Нет портативного способа добиться этого. В Mac OS X решением будет использование LSOpenCFURLRef или другой API LaunchServices, чтобы открыть URL-адрес с обработчиком по умолчанию для схемы URL-адресов. Другие платформы будут действовать по-другому.

person Community    schedule 23.12.2009