eas-cli
Version:
EAS command line tool
161 lines (160 loc) • 6.56 kB
JavaScript
;
Object.defineProperty(exports, "__esModule", { value: true });
exports.validatePNGsForManagedProjectAsync = exports.checkGoogleServicesFileAsync = exports.checkNodeEnvVariable = void 0;
const tslib_1 = require("tslib");
const eas_build_job_1 = require("@expo/eas-build-job");
const core_1 = require("@oclif/core");
const fs_extra_1 = tslib_1.__importDefault(require("fs-extra"));
const path_1 = tslib_1.__importDefault(require("path"));
const semver_1 = tslib_1.__importDefault(require("semver"));
const log_1 = tslib_1.__importStar(require("../log"));
const image_1 = require("../utils/image");
function checkNodeEnvVariable(ctx) {
if (ctx.env?.NODE_ENV === 'production') {
log_1.default.warn('You set NODE_ENV=production in the build profile or environment variables. Remember that it will be available during the entire build process. In particular, it will make yarn/npm install only production packages.');
log_1.default.newLine();
}
}
exports.checkNodeEnvVariable = checkNodeEnvVariable;
async function checkGoogleServicesFileAsync(ctx) {
if (ctx.workflow === eas_build_job_1.Workflow.GENERIC || ctx.buildProfile?.env?.GOOGLE_SERVICES_FILE) {
return;
}
const googleServicesFilePath = ctx.exp[ctx.platform]?.googleServicesFile;
if (!googleServicesFilePath) {
return;
}
const googleServicesEnvVar = ctx.platform === eas_build_job_1.Platform.ANDROID
? ctx.env.GOOGLE_SERVICES_JSON
: ctx.env.GOOGLE_SERVICES_INFO_PLIST;
const rootDir = path_1.default.normalize(await ctx.vcsClient.getRootPathAsync());
const absGoogleServicesFilePath = path_1.default.resolve(ctx.projectDir, googleServicesFilePath);
if ((await fs_extra_1.default.pathExists(absGoogleServicesFilePath)) &&
(!isInsideDirectory(absGoogleServicesFilePath, rootDir) ||
(await ctx.vcsClient.isFileIgnoredAsync(path_1.default.relative(rootDir, absGoogleServicesFilePath)))) &&
!googleServicesEnvVar) {
log_1.default.warn(`File specified via "${ctx.platform}.googleServicesFile" field in your app.json is not checked in to your repository and won't be uploaded to the builder.`);
log_1.default.warn(`Use EAS file environment variables with secret or sensitive visibility to pass all values that you don't want to include in your version control to build process. ${(0, log_1.learnMore)('https://docs.expo.dev/eas/environment-variables/#file-environment-variables')}`);
log_1.default.newLine();
}
}
exports.checkGoogleServicesFileAsync = checkGoogleServicesFileAsync;
function isInsideDirectory(file, directory) {
return file.startsWith(directory);
}
async function validatePNGsForManagedProjectAsync(ctx) {
if (ctx.workflow !== eas_build_job_1.Workflow.MANAGED) {
return;
}
// don't run PNG checks on SDK 47 and newer
// see https://github.com/expo/eas-cli/pull/1477#issuecomment-1293914917
if (!ctx.exp.sdkVersion || semver_1.default.satisfies(ctx.exp.sdkVersion, '>= 47.0.0')) {
return;
}
if (ctx.platform === eas_build_job_1.Platform.ANDROID) {
await validateAndroidPNGsAsync(ctx);
}
// Validating iOS PNGs is currently disabled
// See https://github.com/expo/eas-cli/pull/1477 for context
//
// else {
// await validateIosPNGsAsync(ctx as CommonContext<Platform.IOS>);
// }
}
exports.validatePNGsForManagedProjectAsync = validatePNGsForManagedProjectAsync;
async function validateAndroidPNGsAsync(ctx) {
const pngs = [
{
configPath: 'exp.icon',
pngPath: ctx.exp.icon,
},
{
configPath: 'exp.android.icon',
pngPath: ctx.exp.android?.icon,
},
{
configPath: 'exp.android.adaptiveIcon.foregroundImage',
pngPath: ctx.exp.android?.adaptiveIcon?.foregroundImage,
},
{
configPath: 'exp.android.adaptiveIcon.backgroundImage',
pngPath: ctx.exp.android?.adaptiveIcon?.backgroundImage,
},
{
configPath: 'exp.splash.image',
pngPath: ctx.exp.splash?.image,
},
{
configPath: 'exp.notification.icon',
pngPath: ctx.exp.notification?.icon,
},
];
await validatePNGsAsync(pngs);
}
// Validating iOS PNGs is currently disabled
// See https://github.com/expo/eas-cli/pull/1477 for context
//
// async function validateIosPNGsAsync(ctx: CommonContext<Platform.IOS>): Promise<void> {
// const pngs: ConfigPng[] = [
// {
// configPath: 'exp.icon',
// pngPath: ctx.exp.icon,
// },
// {
// configPath: 'exp.ios.icon',
// pngPath: ctx.exp.ios?.icon,
// },
// {
// configPath: 'exp.splash.image',
// pngPath: ctx.exp.splash?.image,
// },
// {
// configPath: 'exp.notification.icon',
// pngPath: ctx.exp.notification?.icon,
// },
// ];
// await validatePNGsAsync(pngs);
// const icon = ctx.exp.ios?.icon ?? ctx.exp.icon;
// if (!icon) {
// return;
// }
// const iconConfigPath = `expo${ctx.exp.ios?.icon ? '.ios' : ''}.icon`;
// try {
// await ensurePNGIsNotTransparentAsync(icon);
// } catch (err: any) {
// if (err instanceof ImageTransparencyError) {
// Log.error(
// `Your iOS app icon (${iconConfigPath}) can't have transparency if you wish to upload your app to the Apple App Store.`
// );
// Log.error(learnMore('https://expo.fyi/remove-alpha-channel', { dim: false }));
// Errors.exit(1);
// } else {
// throw err;
// }
// }
// }
async function validatePNGsAsync(configPngs) {
const validationPromises = configPngs.map(configPng => validatePNGAsync(configPng));
const validationResults = await Promise.allSettled(validationPromises);
const failedValidations = validationResults.filter((result) => result.status === 'rejected');
if (failedValidations.length === 0) {
return;
}
log_1.default.error('PNG images validation failed:');
for (const { reason } of failedValidations) {
const error = reason;
log_1.default.error(`- ${error.message}`);
}
core_1.Errors.exit(1);
}
async function validatePNGAsync({ configPath, pngPath }) {
if (!pngPath) {
return;
}
if (!pngPath.endsWith('.png')) {
throw new Error(`"${configPath}" is not a PNG file`);
}
if (!(await (0, image_1.isPNGAsync)(pngPath))) {
throw new Error(`"${configPath}" is not valid PNG`);
}
}