Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Outset 4.1.2 #53

Merged
merged 17 commits into from
Apr 18, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
24 changes: 24 additions & 0 deletions MDM/Jamf Pro/service-status-ea.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
#!/bin/zsh

# Indicate if all the Outset daemons are enabled or not.

outsetStatusRaw=$(/usr/local/outset/outset --service-status)
enabledDaemons=$(echo $outsetStatusRaw | grep -c 'Enabled$')

# If there is no user logged in, none of the 3 agents will be active, only the daemons.

expectedServices=6

currentUser=$( echo "show State:/Users/ConsoleUser" | scutil | awk '/Name :/ { print $3 }' )

if [ -z "$currentUser" -o "$currentUser" = "loginwindow" ]; then
expectedServices=3
fi

healthyStatus="Not Healthy"

if [ $enabledDaemons -eq $expectedServices ]; then
healthyStatus="Healthy"
fi

echo "<result>$healthyStatus</result>"
8 changes: 4 additions & 4 deletions Outset.xcodeproj/project.pbxproj
Original file line number Diff line number Diff line change
Expand Up @@ -512,7 +512,7 @@
"@executable_path/../Frameworks",
);
MACOSX_DEPLOYMENT_TARGET = 10.15;
MARKETING_VERSION = 4.1.1;
MARKETING_VERSION = 4.1.2;
PRODUCT_BUNDLE_IDENTIFIER = io.macadmins.Outset;
PRODUCT_NAME = "$(TARGET_NAME)";
PROVISIONING_PROFILE_SPECIFIER = "";
Expand Down Expand Up @@ -549,7 +549,7 @@
"@executable_path/../Frameworks",
);
MACOSX_DEPLOYMENT_TARGET = 10.15;
MARKETING_VERSION = 4.1.1;
MARKETING_VERSION = 4.1.2;
PRODUCT_BUNDLE_IDENTIFIER = io.macadmins.Outset;
PRODUCT_NAME = "$(TARGET_NAME)";
PROVISIONING_PROFILE_SPECIFIER = "";
Expand Down Expand Up @@ -587,7 +587,7 @@
LD_RUNPATH_SEARCH_PATHS = "@executable_path/Frameworks";
"LD_RUNPATH_SEARCH_PATHS[sdk=macosx*]" = "@executable_path/../Frameworks";
MACOSX_DEPLOYMENT_TARGET = 10.15;
MARKETING_VERSION = 4.1.1;
MARKETING_VERSION = 4.1.2;
PRODUCT_BUNDLE_IDENTIFIER = io.macadmins.Outset;
PRODUCT_NAME = "$(TARGET_NAME)";
PROVISIONING_PROFILE_SPECIFIER = "";
Expand Down Expand Up @@ -629,7 +629,7 @@
LD_RUNPATH_SEARCH_PATHS = "@executable_path/Frameworks";
"LD_RUNPATH_SEARCH_PATHS[sdk=macosx*]" = "@executable_path/../Frameworks";
MACOSX_DEPLOYMENT_TARGET = 10.15;
MARKETING_VERSION = 4.1.1;
MARKETING_VERSION = 4.1.2;
PRODUCT_BUNDLE_IDENTIFIER = io.macadmins.Outset;
PRODUCT_NAME = "$(TARGET_NAME)";
PROVISIONING_PROFILE_SPECIFIER = "";
Expand Down
4 changes: 2 additions & 2 deletions Outset/Info.plist
Original file line number Diff line number Diff line change
Expand Up @@ -15,9 +15,9 @@
<key>CFBundlePackageType</key>
<string>$(PRODUCT_BUNDLE_PACKAGE_TYPE)</string>
<key>CFBundleShortVersionString</key>
<string>4.1.1</string>
<string>4.1.2</string>
<key>CFBundleVersion</key>
<string>4.1.1</string>
<string>4.1.2</string>
<key>LSApplicationCategoryType</key>
<string>public.app-category.utilities</string>
<key>LSMinimumSystemVersion</key>
Expand Down
27 changes: 11 additions & 16 deletions Outset/Outset.swift
Original file line number Diff line number Diff line change
Expand Up @@ -161,7 +161,7 @@ struct Outset: ParsableCommand {
// perform log file rotation
performLogRotation(logFolderPath: logDirectory, logFileBaseName: logFileName, maxLogFiles: logFileMaxCount)

writeLog("Processing scheduled runs for boot", logLevel: .debug)
writeLog("Processing scheduled runs for boot", logLevel: .info)
ensureWorkingFolders()

writeOutsetPreferences(prefs: prefs)
Expand Down Expand Up @@ -190,15 +190,15 @@ struct Outset: ParsableCommand {
}

if loginWindow {
writeLog("Processing scheduled runs for login window", logLevel: .debug)
writeLog("Processing scheduled runs for login window", logLevel: .info)

if !folderContents(path: loginWindowDir).isEmpty {
processItems(loginWindowDir)
}
}

if login {
writeLog("Processing scheduled runs for login", logLevel: .debug)
writeLog("Processing scheduled runs for login", logLevel: .info)
if !prefs.ignoredUsers.contains(consoleUser) {
if !folderContents(path: loginOnceDir).isEmpty {
processItems(loginOnceDir, once: true, override: prefs.overrideLoginOnce)
Expand All @@ -207,14 +207,14 @@ struct Outset: ParsableCommand {
processItems(loginEveryDir)
}
if !folderContents(path: loginOncePrivilegedDir).isEmpty || !folderContents(path: loginEveryPrivilegedDir).isEmpty {
FileManager.default.createFile(atPath: loginPrivilegedTrigger, contents: nil)
createTrigger(loginPrivilegedTrigger)
}
}

}

if loginPrivileged {
writeLog("Processing scheduled runs for privileged login", logLevel: .debug)
writeLog("Processing scheduled runs for privileged login", logLevel: .info)
if checkFileExists(path: loginPrivilegedTrigger) {
pathCleanup(pathname: loginPrivilegedTrigger)
}
Expand All @@ -231,29 +231,24 @@ struct Outset: ParsableCommand {
}

if onDemand {
writeLog("Processing on-demand", logLevel: .debug)
writeLog("Processing on-demand", logLevel: .info)
if !folderContents(path: onDemandDir).isEmpty {
if !["root", "loginwindow"].contains(consoleUser) {
let currentUser = NSUserName()
if consoleUser == currentUser {
processItems(onDemandDir)
createTrigger(cleanupTrigger)
} else {
writeLog("User \(currentUser) is not the current console user. Skipping on-demand run.")
}
} else {
writeLog("No current user session. Skipping on-demand run.")
}
FileManager.default.createFile(atPath: cleanupTrigger, contents: nil)
DispatchQueue.main.asyncAfter(deadline: .now() + 0.5) {
if checkFileExists(path: cleanupTrigger) {
pathCleanup(pathname: cleanupTrigger)
}
}
}
}

if loginEvery {
writeLog("Processing scripts in login-every", logLevel: .debug)
writeLog("Processing scripts in login-every", logLevel: .info)
if !prefs.ignoredUsers.contains(consoleUser) {
if !folderContents(path: loginEveryDir).isEmpty {
processItems(loginEveryDir)
Expand All @@ -262,7 +257,7 @@ struct Outset: ParsableCommand {
}

if loginOnce {
writeLog("Processing scripts in login-once", logLevel: .debug)
writeLog("Processing scripts in login-once", logLevel: .info)
if !prefs.ignoredUsers.contains(consoleUser) {
if !folderContents(path: loginOnceDir).isEmpty {
processItems(loginOnceDir, once: true, override: prefs.overrideLoginOnce)
Expand All @@ -273,7 +268,7 @@ struct Outset: ParsableCommand {
}

if cleanup {
writeLog("Cleaning up on-demand directory.", logLevel: .debug)
writeLog("Cleaning up on-demand directory.", logLevel: .info)
if checkFileExists(path: onDemandTrigger) { pathCleanup(pathname: onDemandTrigger) }
if checkFileExists(path: cleanupTrigger) { pathCleanup(pathname: cleanupTrigger) }
if !folderContents(path: onDemandDir).isEmpty { pathCleanup(pathname: onDemandDir) }
Expand Down Expand Up @@ -309,7 +304,7 @@ struct Outset: ParsableCommand {
ensureRoot("add scripts to override list")

for var override in addOverride {
if !override.contains(loginOnceDir) {
if !override.contains(loginOnceDir) && !override.contains(loginOncePrivilegedDir) {
override = "\(loginOnceDir)/\(override)"
}
writeLog("Adding \(override) to override list", logLevel: .debug)
Expand Down
4 changes: 4 additions & 0 deletions Outset/Utils/FileUtils.swift
Original file line number Diff line number Diff line change
Expand Up @@ -169,6 +169,10 @@ func deletePath(_ path: String) {
}
}

func createTrigger(_ path: String) {
FileManager.default.createFile(atPath: path, contents: nil)
}

func mountDmg(dmg: String) -> String {
// Attaches dmg and returns the path
let cmd = "/usr/bin/hdiutil attach -nobrowse -noverify -noautoopen \(dmg)"
Expand Down
4 changes: 2 additions & 2 deletions Outset/Utils/ItemProcessing.swift
Original file line number Diff line number Diff line change
Expand Up @@ -85,7 +85,7 @@ func processItems(_ path: String, deleteItems: Bool=false, once: Bool=false, ove
}

if once {
writeLog("Processing run-once \(script)", logLevel: .debug)
writeLog("Processing run-once \(script)", logLevel: .info)
// If this is supposed to be a runonce item then we want to check to see if has an existing runonce entry
// looks for a key with the full script path. Writes the full path and run date when done
if !runOnceDict.contains(where: {$0.key == script}) {
Expand Down Expand Up @@ -119,7 +119,7 @@ func processItems(_ path: String, deleteItems: Bool=false, once: Bool=false, ove
}
}
} else {
writeLog("Processing script \(script)", logLevel: .debug)
writeLog("Processing script \(script)", logLevel: .info)
let (_, error, status) = runShellCommand(script, args: [consoleUser], verbose: true)
if status != 0 {
writeLog(error, logLevel: .error)
Expand Down
19 changes: 10 additions & 9 deletions Outset/Utils/Preferences.swift
Original file line number Diff line number Diff line change
Expand Up @@ -153,16 +153,17 @@ func migrateLegacyPreferences() {
deletePath(newoldRootUserDefaults)
}
case legacyOutsetPreferencesFile:
writeLog("\(legacyOutsetPreferencesFile) migration", logLevel: .debug)
do {
let legacyPreferences = try PropertyListDecoder().decode(OutsetPreferences.self, from: data)
writeOutsetPreferences(prefs: legacyPreferences)
writeLog("Migrated Legacy Outset Preferences", logLevel: .debug)
deletePath(legacyOutsetPreferencesFile)
} catch {
writeLog("legacy Preferences migration failed", logLevel: .error)
if isRoot() {
writeLog("\(legacyOutsetPreferencesFile) migration", logLevel: .debug)
do {
let legacyPreferences = try PropertyListDecoder().decode(OutsetPreferences.self, from: data)
writeOutsetPreferences(prefs: legacyPreferences)
writeLog("Migrated Legacy Outset Preferences", logLevel: .debug)
deletePath(legacyOutsetPreferencesFile)
} catch {
writeLog("legacy Preferences migration failed", logLevel: .error)
}
}

case legacyRootRunOncePlistFile, legacyUserRunOncePlistFile:
writeLog("\(legacyRootRunOncePlistFile) and \(legacyUserRunOncePlistFile) migration", logLevel: .debug)
do {
Expand Down
51 changes: 49 additions & 2 deletions Package/outset-pkg
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@
# AUTHOR: Bart Reardon
# ORGANIZATION: Macadmins Open Source
# CREATED: 2023-03-23
# REVISION: 1.0.1
# REVISION: 1.0.2
#
# COPYRIGHT: (C) Macadmins Open Source 2023. All rights reserved.
#
Expand All @@ -21,6 +21,9 @@
FILE_TO_PACKAGE=""
FILE_TARGET="login-once"
BUILD_ALL=false
POSTINSTALL_SCRIPT=false
MAKE_EXECUTABLE=false
POSTINSTALL_SCRIPT_FILE=""
BUILD_DIRECTORY="/var/tmp/outset"

PKGTITLE="Outset Custom Content"
Expand All @@ -30,7 +33,16 @@ PKGID="${PKG_DOMAIN}.custom-content"

OUTSET_ROOT="/usr/local/outset"
PGKROOT="${BUILD_DIRECTORY}/PGKROOT"
SCRIPT_DIR="${PGKROOT}/scripts"
PKGNAME="outset-custom-content"
ONDEMAND_POSTINSTALL=$(cat <<EOF
#!/bin/bash
trigger="/private/tmp/.io.macadmins.outset.ondemand.launchd"
[[ \$3 != "/" ]] && exit 0
/usr/bin/touch "\${trigger}"
exit 0
EOF
)

printUsage() {
echo "OVERVIEW: ${0##*/} is a utility that packages files for use in outset workflows."
Expand All @@ -40,7 +52,11 @@ printUsage() {
echo "OPTIONS:"
echo " -a, --all Package all scripts from outset processing directories into one package"
echo " -f, --file <filename> Package the selected file"
echo " -x, --make-executable Ensure the selected file executable bit is set (only applies to script files)"
echo " -t, --target <directory> Target processing directory (default 'login-once')"
echo " -s, --postinstall-script [<filename>]"
echo " Include a postinstall script. If no argument is given, a standard postinstall"
echo " script to trigger on-demand will be included."
echo " -v, --version, <number> Set package version to the selected number (default is '1.0')"
echo " -p, --build-path, <path> Path to use as the build location (default ${BUILD_DIRECTORY})"
echo " -h, --help Print this message"
Expand Down Expand Up @@ -95,8 +111,17 @@ fi
while [[ "$#" -gt 0 ]]; do
case $1 in
--file|-f) FILE_TO_PACKAGE="$2"; shift ;;
--make-executable|-x) MAKE_EXECUTABLE=true ;;
--target|-t) FILE_TARGET=$(validateTarget "$2") || printValidTargets "$2"; shift ;;
--version|-v) PKGVERSION=$(validateVersion "$2") || exitWithError "invalid version number $2"; shift ;;
--postinstall-script|-s) POSTINSTALL_SCRIPT_FILE="$2" && POSTINSTALL_SCRIPT=true
# if the first character is a hyphen, then no argument was passed
if [[ -z $POSTINSTALL_SCRIPT_FILE ]] || [[ "${POSTINSTALL_SCRIPT_FILE:0:1}" == "-" ]]; then
POSTINSTALL_SCRIPT_FILE=""
else
shift
fi
;;
--build-path|-p)
if [[ -e "$2" ]]; then
BUILD_DIRECTORY="${2%/}"
Expand All @@ -116,6 +141,20 @@ done
# create PGKROOT structure
mkdir -p "${PGKROOT}${OUTSET_ROOT}"

if $POSTINSTALL_SCRIPT; then
mkdir -p "${SCRIPT_DIR}"
if [[ -n $POSTINSTALL_SCRIPT_FILE ]]; then
if [[ -e "${POSTINSTALL_SCRIPT_FILE}" ]]; then
cp "${POSTINSTALL_SCRIPT_FILE}" "${SCRIPT_DIR}/postinstall"
else
exitWithError "${POSTINSTALL_SCRIPT_FILE} doesn't exist"
fi
else
echo "${ONDEMAND_POSTINSTALL}" > "${SCRIPT_DIR}/postinstall"
fi
chmod 755 "${SCRIPT_DIR}/postinstall"
fi

if [[ -n $FILE_TO_PACKAGE ]]; then
PKGID="${PKG_DOMAIN}.${FILE_TARGET}-${FILE_TO_PACKAGE##*/}"
PKGNAME="outset-${FILE_TARGET}-${FILE_TO_PACKAGE##*/}_v${PKGVERSION}"
Expand All @@ -125,6 +164,10 @@ if [[ -n $FILE_TO_PACKAGE ]]; then

if [[ -e "${FILE_TO_PACKAGE}" ]]; then
cp "${FILE_TO_PACKAGE}" "${TARGET_DIR}"
# if the file is not a pkg or dmg, make it executable
if $MAKE_EXECUTABLE && [[ "${FILE_TO_PACKAGE##*.}" != "pkg" ]] && [[ "${FILE_TO_PACKAGE##*.}" != "dmg" ]]; then
chmod 755 "${TARGET_DIR}/${FILE_TO_PACKAGE##*/}"
fi
else
exitWithError "${FILE_TO_PACKAGE} doesn't exist"
fi
Expand All @@ -139,7 +182,11 @@ fi
TMP_PKG="${BUILD_DIRECTORY}/${PKGNAME}.component.pkg"
BUILD_PKG="${BUILD_DIRECTORY}/${PKGNAME}.pkg"

/usr/bin/pkgbuild --root "${PGKROOT}" --identifier ${PKGID} --version ${PKGVERSION} "${TMP_PKG}"
if $POSTINSTALL_SCRIPT; then
/usr/bin/pkgbuild --root "${PGKROOT}" --scripts "${SCRIPT_DIR}" --identifier ${PKGID} --version ${PKGVERSION} "${TMP_PKG}"
else
/usr/bin/pkgbuild --root "${PGKROOT}" --identifier ${PKGID} --version ${PKGVERSION} "${TMP_PKG}"
fi
/usr/bin/productbuild --identifier ${PKGID} --package "${TMP_PKG}" "${BUILD_PKG}"

# clean up
Expand Down
Loading
Loading