UNPKG

penguins-eggs

Version:

A remaster system tool, compatible with Arch, Debian, Devuan, Ubuntu and others

294 lines (293 loc) 12.1 kB
/** * ./src/classes/ovary.d/produce.ts * penguins-eggs v.10.0.0 / ecmascript 2020 * author: Piero Proietti * email: piero.proietti@gmail.com * license: MIT */ import chalk from 'chalk'; import mustache from 'mustache'; // packages import fs from 'node:fs'; import shx from 'shelljs'; import path from 'path'; // libraries import { exec } from '../../lib/utils.js'; import Bleach from './../bleach.js'; import { displaymanager } from './../incubation/fisherman-helper/displaymanager.js'; import Incubator from './../incubation/incubator.js'; import Pacman from './../pacman.js'; import Diversions from './../diversions.js'; // classes import Utils from './../utils.js'; import Repo from './../yolk.js'; // _dirname const __dirname = path.dirname(new URL(import.meta.url).pathname); /** * produce * @param clone * @param cryptedclone * @param scriptOnly * @param yolkRenew * @param release * @param myAddons * @param nointeractive * @param noicons * @param unsecure * @param verbose */ export async function produce(kernel = '', clone = false, cryptedclone = false, scriptOnly = false, yolkRenew = false, release = false, myAddons, myLinks, excludes, nointeractive = false, noicons = false, unsecure = false, verbose = false) { this.verbose = verbose; this.echo = Utils.setEcho(verbose); if (this.verbose) { this.toNull = ' > /dev/null 2>&1'; } this.kernel = kernel; this.clone = clone; this.cryptedclone = cryptedclone; const luksName = 'luks-volume'; const luksFile = `/tmp/${luksName}`; /** * define kernel */ if (this.kernel === '') { if (this.familyId === 'alpine') { // to do } else if (this.familyId === 'archlinux') { const moduleDirs = fs.readdirSync('/usr/lib/modules'); this.kernel = moduleDirs[0]; /** * no need more */ if (Diversions.isManjaroBased(this.distroId)) { // this.kernel += '-MANJARO' } } else { // debian, fedora, openmamba, opensuse, voidlinux let vmlinuz = path.basename(Utils.vmlinuz()); this.kernel = vmlinuz.substring(vmlinuz.indexOf('-') + 1); } } /** * define this.vmlinuz */ this.vmlinuz = Utils.vmlinuz(); /** * define this.initrd */ this.initrd = Utils.initrdImg(this.kernel); /** * yolk */ if (this.familyId === 'debian' && Utils.uefiArch() === 'amd64') { const yolk = new Repo(); if (!yolk.exists()) { Utils.warning('creating yolk'); await yolk.create(verbose); } else if (yolkRenew) { Utils.warning('refreshing yolk'); await yolk.erase(); await yolk.create(verbose); } else { Utils.warning('using preesixent yolk'); } } if (!fs.existsSync(this.settings.config.snapshot_dir)) { shx.mkdir('-p', this.settings.config.snapshot_dir); } if (Utils.isLive()) { console.log(chalk.red('>>> eggs: This is a live system! An egg cannot be produced from an egg!')); } else { await this.liveCreateStructure(); // Carica calamares solo se le icone sono accettate if (!noicons && // se VOGLIO le icone !nointeractive && this.settings.distro.isCalamaresAvailable && Pacman.isInstalledGui() && this.settings.config.force_installer && !Pacman.calamaresExists()) { console.log('Installing ' + chalk.bgGray('calamares') + ' due force_installer=yes.'); await Pacman.calamaresInstall(verbose); const bleach = new Bleach(); await bleach.clean(verbose); } if (cryptedclone) { /** * cryptedclone */ console.log("eggs will SAVE users and users' data ENCRYPTED"); } else if (this.clone) { /** * clone */ this.settings.config.user_opt = 'live'; // patch for humans this.settings.config.user_opt_passwd = 'evolution'; this.settings.config.root_passwd = 'evolution'; Utils.warning("eggs will SAVE users and users' data UNCRYPTED on the live"); } else { /** * normal */ Utils.warning("eggs will REMOVE users and users' data from live"); } /** * exclude.list */ if (!excludes.static && !fs.existsSync('/etc/penguins-eggs/exclude.list')) { const excludeListTemplateDir = '/etc/penguins-eggs.d/exclude.list.d/'; const excludeListTemplate = excludeListTemplateDir + 'master.list'; if (!fs.existsSync(excludeListTemplate)) { Utils.warning('Cannot find: ' + excludeListTemplate); process.exit(1); } let excludeUsr = ''; let excludeVar = ''; let excludeHomes = ''; let excludeHome = ''; if (excludes.usr) { excludeUsr = fs.readFileSync(`${excludeListTemplateDir}usr.list`, 'utf8'); } if (excludes.var) { excludeVar = fs.readFileSync(`${excludeListTemplateDir}var.list`, 'utf8'); } if (excludes.homes) { excludeHomes = fs.readFileSync(`${excludeListTemplateDir}homes.list`, 'utf8'); } if (excludes.home) { excludeHome = `home/${await Utils.getPrimaryUser()}/*`; } const view = { home_list: excludeHome, homes_list: excludeHomes, usr_list: excludeUsr, var_list: excludeVar }; const template = fs.readFileSync(excludeListTemplate, 'utf8'); fs.writeFileSync(this.settings.config.snapshot_excludes, mustache.render(template, view)); } /** * NOTE: reCreate = false * * reCreate = false is just for develop * put reCreate = true in release */ const reCreate = true; let mksquashfsCmd = ''; if (reCreate) { // start pre-clone /** * installer */ this.incubator = new Incubator(this.settings.remix, this.settings.distro, this.settings.config.user_opt, this.theme, this.clone, verbose); await this.incubator.config(release); await this.syslinux(this.theme); await this.kernelCopy(); /** * differents initrd for different families */ if (this.familyId === 'alpine') { await this.initrdAlpine(); } else if (this.familyId === 'archlinux') { await this.initrdArch(); } else if (this.familyId === 'debian') { await this.initrdDebian(); } else if (this.familyId === 'fedora' || this.familyId === 'openmamba' || this.familyId === 'opensuse' || this.familyId === 'voidlinux') { await this.initrdDracut(); } if (this.settings.config.make_efi) { await this.makeEfi(this.theme); } await this.bindLiveFs(); if (!this.clone) { /** * ANCHE per cryptedclone */ await this.usersRemove(); await this.userCreateLive(); if (Pacman.isInstalledGui()) { await this.createXdgAutostart(this.settings.config.theme, myAddons, myLinks, noicons); /** * GUI installed but NOT Desktop Manager: just create motd and issue */ if (displaymanager().length > 0) { this.cliAutologin.addIssue(this.settings.distro.distroId, this.settings.distro.codenameId, this.settings.config.user_opt, this.settings.config.user_opt_passwd, this.settings.config.root_passwd, this.settings.work_dir.merged); this.cliAutologin.addMotd(this.settings.distro.distroId, this.settings.distro.codenameId, this.settings.config.user_opt, this.settings.config.user_opt_passwd, this.settings.config.root_passwd, this.settings.work_dir.merged); } } else { this.cliAutologin.add(this.settings.distro.distroId, this.settings.distro.codenameId, this.settings.config.user_opt, this.settings.config.user_opt_passwd, this.settings.config.root_passwd, this.settings.work_dir.merged); } } await this.editLiveFs(clone, cryptedclone); mksquashfsCmd = await this.makeSquashfs(scriptOnly, unsecure); await this.uBindLiveFs(); // Lo smonto prima della fase di backup } if (cryptedclone) { let synctoCmd = `eggs syncto -f ${luksFile}`; if (excludes.home) { synctoCmd += ' --excludes'; // from Marco, usa home.list } await exec(synctoCmd, Utils.setEcho(true)); Utils.warning(`moving ${luksFile} in ${this.nest}iso/live`); await exec(`mv ${luksFile} ${this.nest}iso/live`, this.echo); } const mkIsofsCmd = (await this.xorrisoCommand(clone, cryptedclone)).replaceAll(/\s\s+/g, ' '); this.makeDotDisk(this.volid, mksquashfsCmd, mkIsofsCmd); /** * AntiX/MX LINUX */ if (fs.existsSync('/etc/antix-version')) { let uname = (await exec('uname -r', { capture: true })).data; uname = uname.replaceAll('\n', ''); let content = ''; content = '#!/usr/bin/env bash'; content += 'mkdir /live/bin -p\n'; content += '## \n'; content += '# cp /usr/lib/penguins-eggs/scripts/non-live-cmdline /live/bin -p\n'; content += '# chmod +x /live/bin/non-live-cmdline\n'; content += '## \n'; content += 'mkdir /live/boot-dev/antiX -p\n'; content += 'ln -s /run/live/medium/live/filesystem.squashfs /live/boot-dev/antiX/linuxfs\n'; content += `ln -s /run/live/medium/live/initrd.img-${uname} /live/boot-dev/antiX/initrd.gz\n`; content += `ln -s /run/live/medium/live/vmlinuz-${uname} /live/boot-dev/antiX/vmlinuz\n`; content += `# md5sum /live/boot-dev/antiX/linuxfs > /live/boot-dev/antiX/linuxfs.md5\n`; content += `# md5sum /live/boot-dev/antiX/initrd.gz > /live/boot-dev/antiX/initrd.gz.md5\n`; content += `# md5sum /live/boot-dev/antiX/vmlinuz > /live/boot-dev/antiX/vmlinuz.md5\n`; content += `# /live/aufs -> /run/live/rootfs/filesystem.squashfs\n`; content += 'ln -s /run/live/rootfs/filesystem.squashfs /live/aufs\n'; content += `# use: minstall -no-media-check\n`; content += 'minstall --no-media-check\n'; const file = `${this.settings.iso_work}antix-mx-installer`; fs.writeFileSync(file, content); await exec(`chmod +x ${file}`); } /** * patch to emulate miso/archiso on archilinux family */ if (this.familyId === 'archlinux') { let pathName = `arch/x86_64/airootfs`; let hashCmd = 'sha512sum'; let hashExt = '.sha512'; if (Diversions.isManjaroBased(this.settings.distro.distroId)) { pathName = `manjaro/x86_64/livefs`; hashCmd = `md5sum`; hashExt = '.md5'; } await exec(`mkdir ${this.settings.iso_work}${pathName}/x86_64 -p`, this.echo); fs.linkSync(`${this.settings.iso_work}live/filesystem.squashfs`, `${this.settings.iso_work}${pathName}.sfs`); } await this.makeIso(mkIsofsCmd, scriptOnly); } }