Open Wizzel1 opened 1 year ago
The .local-chromium
directory is relative to the current working directory of the app.
In your case, it can be better to download the binaries to an app-specific storage location (downloadChrome(cachePath:)
) and always specify the absolute executable path when launching puppeteer (puppeteer.launch(executablePath:)
).
Here is a small example:
import 'package:path/path.dart' as path;
import 'dart:io';
import 'package:puppeteer/puppeteer.dart';
void main() async {
// 1. Control the location where the app download the chromium binaries
var appStorage = applicationConfigHome('puppeteer-app');
var chromePath = await downloadChrome(cachePath: path.join(appStorage, 'chromium'));
// 2. Always specify the full path
var browser = await puppeteer.launch(executablePath: chromePath.executablePath);
await browser.close();
}
// ==========
// Utilities copied from https://github.com/dart-lang/cli_util/blob/master/lib/cli_util.dart
/// Get the user-specific application configuration folder for the current
/// platform.
///
/// This is a location appropriate for storing application specific
/// configuration for the current user. The [productName] should be unique to
/// avoid clashes with other applications on the same machine. This method won't
/// actually create the folder, merely return the recommended location for
/// storing user-specific application configuration.
///
/// The folder location depends on the platform:
/// * `%APPDATA%\<productName>` on **Windows**,
/// * `$HOME/Library/Application Support/<productName>` on **Mac OS**,
/// * `$XDG_CONFIG_HOME/<productName>` on **Linux**
/// (if `$XDG_CONFIG_HOME` is defined), and,
/// * `$HOME/.config/<productName>` otherwise.
///
/// This aims follows best practices for each platform, honoring the
/// [XDG Base Directory Specification][1] on Linux and [File System Basics][2]
/// on Mac OS.
///
/// Throws an [EnvironmentNotFoundException] if `%APPDATA%` or `$HOME` is needed
/// but undefined.
///
/// [1]: https://specifications.freedesktop.org/basedir-spec/basedir-spec-latest.html
/// [2]: https://developer.apple.com/library/archive/documentation/FileManagement/Conceptual/FileSystemProgrammingGuide/FileSystemOverview/FileSystemOverview.html#//apple_ref/doc/uid/TP40010672-CH2-SW1
String applicationConfigHome(String productName) =>
path.join(_configHome, productName);
String get _configHome {
if (Platform.isWindows) {
final appdata = Platform.environment['APPDATA'];
if (appdata == null) {
throw Exception(
'Environment variable %APPDATA% is not defined!');
}
return appdata;
}
if (Platform.isMacOS) {
return path.join(_home, 'Library', 'Application Support');
}
if (Platform.isLinux) {
final xdgConfigHome = Platform.environment['XDG_CONFIG_HOME'];
if (xdgConfigHome != null) {
return xdgConfigHome;
}
// XDG Base Directory Specification says to use $HOME/.config/ when
// $XDG_CONFIG_HOME isn't defined.
return path.join(_home, '.config');
}
// We have no guidelines, perhaps we should just do: $HOME/.config/
// same as XDG specification would specify as fallback.
return path.join(_home, '.config');
}
String get _home {
final home = Platform.environment['HOME'];
if (home == null) {
throw Exception(
r'Environment variable $HOME is not defined!');
}
return home;
}
@xvrh yes that worked, thank you!
I am wondering if it is even possible to ship the executable with a .local-chromium
folder inside, so users don't have to wait for the first installation?
Also, how would I update the chromium version? Does puppeteer look for a specific chromium version and downloads it, if necessary?
I am wondering if it is even possible to ship the executable with a .local-chromium folder inside, so users don't have to wait for the first installation?
I guess yes it is possible but it depends on how you ship your application...
how would I update the chromium version? Does puppeteer look for a specific chromium version and downloads it, if necessary
Internally the downloadChrome
method (and also puppeteer.launch
if executablePath
is not specified) checks if the version already exists and download it if necessary: https://github.com/xvrh/puppeteer-dart/blob/master/lib/src/downloader.dart#L33
I am building a windows app and I don't ship the
.local-chromium
folder at the root of the project. That means before launching, thedownloadChrome
function gets called which is fine.But for some reason, the
.local-chromium
folder gets installed at the latest path a user has accessed from my app. For example:1) User opens my app 2) User selects an image from his
/desktop
3) User launches puppeteer through my app 4).local-chromium
folder appears at/desktop
. 5) User selects a file from/files
6) Another.local-chromium
folder appears at/files
so the user now has 2 chromium installations on his pc.Why is this happening? I thought it only downloads chromium to the root of my project?