Merge branch 'main' into feat-vpp-apps-18867

This commit is contained in:
Roberto Dip 2024-07-23 14:56:48 -05:00 committed by GitHub
commit a8aeb6bbb7
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
9 changed files with 220 additions and 71 deletions

View file

@ -0,0 +1 @@
- Update profile activities to include iOS and iPadOS

View file

@ -36,9 +36,12 @@ export enum ActivityType {
MdmUnenrolled = "mdm_unenrolled",
EditedMacosMinVersion = "edited_macos_min_version",
ReadHostDiskEncryptionKey = "read_host_disk_encryption_key",
CreatedMacOSProfile = "created_macos_profile",
DeletedMacOSProfile = "deleted_macos_profile",
EditedMacOSProfile = "edited_macos_profile",
/** Note: BE not renamed (yet) from macOS even though activity is also used for iOS and iPadOS */
CreatedAppleOSProfile = "created_macos_profile",
/** Note: BE not renamed (yet) from macOS even though activity is also used for iOS and iPadOS */
DeletedAppleOSProfile = "deleted_macos_profile",
/** Note: BE not renamed (yet) from macOS even though activity is also used for iOS and iPadOS */
EditedAppleOSProfile = "edited_macos_profile",
CreatedWindowsProfile = "created_windows_profile",
DeletedWindowsProfile = "deleted_windows_profile",
EditedWindowsProfile = "edited_windows_profile",

View file

@ -36,10 +36,11 @@ const PREMIUM_ACTIVITIES = new Set([
const getProfileMessageSuffix = (
isPremiumTier: boolean,
platform: "darwin" | "windows",
platform: "apple" | "windows",
teamName?: string | null
) => {
const platformDisplayName = platform === "darwin" ? "macOS" : "Windows";
const platformDisplayName =
platform === "apple" ? "macOS, iOS, and iPadOS" : "Windows";
let messageSuffix = <>all {platformDisplayName} hosts</>;
if (isPremiumTier) {
messageSuffix = teamName ? (
@ -345,7 +346,7 @@ const TAGGED_TEMPLATES = {
</>
);
},
createMacOSProfile: (activity: IActivity, isPremiumTier: boolean) => {
createdAppleOSProfile: (activity: IActivity, isPremiumTier: boolean) => {
const profileName = activity.details?.profile_name;
return (
<>
@ -361,14 +362,14 @@ const TAGGED_TEMPLATES = {
to{" "}
{getProfileMessageSuffix(
isPremiumTier,
"darwin",
"apple",
activity.details?.team_name
)}
.
</>
);
},
deleteMacOSProfile: (activity: IActivity, isPremiumTier: boolean) => {
deletedAppleOSProfile: (activity: IActivity, isPremiumTier: boolean) => {
const profileName = activity.details?.profile_name;
return (
<>
@ -384,28 +385,28 @@ const TAGGED_TEMPLATES = {
from{" "}
{getProfileMessageSuffix(
isPremiumTier,
"darwin",
"apple",
activity.details?.team_name
)}
.
</>
);
},
editMacOSProfile: (activity: IActivity, isPremiumTier: boolean) => {
editedAppleOSProfile: (activity: IActivity, isPremiumTier: boolean) => {
return (
<>
{" "}
edited configuration profiles for{" "}
{getProfileMessageSuffix(
isPremiumTier,
"darwin",
"apple",
activity.details?.team_name
)}{" "}
via fleetctl.
</>
);
},
createWindowsProfile: (activity: IActivity, isPremiumTier: boolean) => {
createdWindowsProfile: (activity: IActivity, isPremiumTier: boolean) => {
const profileName = activity.details?.profile_name;
return (
<>
@ -428,7 +429,7 @@ const TAGGED_TEMPLATES = {
</>
);
},
deleteWindowsProfile: (activity: IActivity, isPremiumTier: boolean) => {
deletedWindowsProfile: (activity: IActivity, isPremiumTier: boolean) => {
const profileName = activity.details?.profile_name;
return (
<>
@ -451,7 +452,7 @@ const TAGGED_TEMPLATES = {
</>
);
},
editWindowsProfile: (activity: IActivity, isPremiumTier: boolean) => {
editedWindowsProfile: (activity: IActivity, isPremiumTier: boolean) => {
return (
<>
{" "}
@ -781,7 +782,7 @@ const TAGGED_TEMPLATES = {
to{" "}
{getProfileMessageSuffix(
isPremiumTier,
"darwin",
"apple",
activity.details?.team_name
)}
.
@ -796,7 +797,7 @@ const TAGGED_TEMPLATES = {
<b>{activity.details?.profile_name}</b> from{" "}
{getProfileMessageSuffix(
isPremiumTier,
"darwin",
"apple",
activity.details?.team_name
)}
.
@ -811,7 +812,7 @@ const TAGGED_TEMPLATES = {
<b>{activity.details?.profile_name}</b> for{" "}
{getProfileMessageSuffix(
isPremiumTier,
"darwin",
"apple",
activity.details?.team_name
)}{" "}
via fleetctl.
@ -1014,26 +1015,27 @@ const getDetail = (
case ActivityType.EditedMacosMinVersion: {
return TAGGED_TEMPLATES.editedMacosMinVersion(activity);
}
case ActivityType.ReadHostDiskEncryptionKey: {
return TAGGED_TEMPLATES.readHostDiskEncryptionKey(activity);
}
case ActivityType.CreatedMacOSProfile: {
return TAGGED_TEMPLATES.createMacOSProfile(activity, isPremiumTier);
case ActivityType.CreatedAppleOSProfile: {
return TAGGED_TEMPLATES.createdAppleOSProfile(activity, isPremiumTier);
}
case ActivityType.DeletedMacOSProfile: {
return TAGGED_TEMPLATES.deleteMacOSProfile(activity, isPremiumTier);
case ActivityType.DeletedAppleOSProfile: {
return TAGGED_TEMPLATES.deletedAppleOSProfile(activity, isPremiumTier);
}
case ActivityType.EditedMacOSProfile: {
return TAGGED_TEMPLATES.editMacOSProfile(activity, isPremiumTier);
case ActivityType.EditedAppleOSProfile: {
return TAGGED_TEMPLATES.editedAppleOSProfile(activity, isPremiumTier);
}
case ActivityType.CreatedWindowsProfile: {
return TAGGED_TEMPLATES.createWindowsProfile(activity, isPremiumTier);
return TAGGED_TEMPLATES.createdWindowsProfile(activity, isPremiumTier);
}
case ActivityType.DeletedWindowsProfile: {
return TAGGED_TEMPLATES.deleteWindowsProfile(activity, isPremiumTier);
return TAGGED_TEMPLATES.deletedWindowsProfile(activity, isPremiumTier);
}
case ActivityType.EditedWindowsProfile: {
return TAGGED_TEMPLATES.editWindowsProfile(activity, isPremiumTier);
return TAGGED_TEMPLATES.editedWindowsProfile(activity, isPremiumTier);
}
// Note: Both "enabled_disk_encryption" and "enabled_macos_disk_encryption" display the same
// message. The latter is deprecated in the API but it is retained here for backwards compatibility.

View file

@ -375,7 +375,7 @@ No later than the second month of every quarter, we check [Delaware divison of c
### Check finances for quirks
Every quarter, we check Quickbooks Online (QBO) for discrepancies and follow up on quirks.
1. Check to make sure [bookkeeping quirks](https://docs.google.com/spreadsheets/d/1nuUPMZb1z_lrbaQEcgjnxppnYv_GWOTTo4FMqLOlsWg/edit?usp=sharing) are all accounted for and resolved or in progress toward resolution.
2. Check balance sheet and profit and loss statements (P&Ls) in QBO against the latest [monthly workbooks](https://drive.google.com/drive/folders/1ben-xJgL5MlMJhIl2OeQpDjbk-pF6eJM) in Google Drive.
2. Check balance sheet and profit and loss statements (P&Ls) in QBO against the latest [monthly workbooks](https://drive.google.com/drive/folders/1ben-xJgL5MlMJhIl2OeQpDjbk-pF6eJM) in Google Drive. Ensure reports are in the "accural" accounting method.
3. Reach out to Pilot with any differences or quirks, and ask them to resolve/provide clarity. This often will need to happen over a call to review sycnhronously.
4. Once quirks are resolved, note the day it was resolved in the spreadsheet.

View file

@ -5,20 +5,20 @@ Following are the currently deployed versions of fleetd components on the `stabl
## `stable`
| Component\OS | macOS | Linux | Windows |
|--------------|--------------|--------|---------|
| orbit | 1.27.0 | 1.27.0 | 1.27.0 |
| desktop | 1.27.0 | 1.27.0 | 1.27.0 |
| osqueryd | 5.12.1 | 5.12.1 | 5.12.1 |
| nudge | 1.1.10.81462 | - | - |
| swiftDialog | 2.1.0 | - | - |
| Component\OS | macOS | Linux | Windows | Linux (arm64) |
|--------------|--------------|--------|---------|---------------|
| orbit | 1.28.0 | 1.28.0 | 1.28.0 | 1.28.0 |
| desktop | 1.28.0 | 1.28.0 | 1.28.0 | 1.28.0 |
| osqueryd | 5.12.1 | 5.12.1 | 5.12.1 | 5.12.1 |
| nudge | 1.1.10.81462 | - | - | - |
| swiftDialog | 2.1.0 | - | - | - |
## `edge`
| Component\OS | macOS | Linux | Windows |
|--------------|--------|--------|---------|
| orbit | 1.28.0 | 1.28.0 | 1.28.0 |
| desktop | 1.28.0 | 1.28.0 | 1.28.0 |
| osqueryd | 5.12.2 | 5.12.2 | 5.12.2 |
| nudge | - | - | - |
| swiftDialog | - | - | - |
| Component\OS | macOS | Linux | Windows | Linux (arm64) |
|--------------|--------|--------|---------|---------------|
| orbit | 1.28.0 | 1.28.0 | 1.28.0 | 1.28.0 |
| desktop | 1.28.0 | 1.28.0 | 1.28.0 | 1.28.0 |
| osqueryd | 5.12.2 | 5.12.2 | 5.12.2 | 5.12.1 |
| nudge | - | - | - | - |
| swiftDialog | - | - | - | - |

View file

@ -0,0 +1,30 @@
## MDM asset extractor
The MDM Asset Extractor is a tool designed to extract all MDM assets from a
Fleet database. The assets are extracted unencrypted; hence, the key used for
encrypting the assets must be provided.
### Usage
During development, a typical usage example would be:
```
go run tools/mdm/assets/main.go -key=E6Ow1t2dbKARxEF6O9GFI3DDQRMROhI8 -dir=mdm_assets
```
Supported flags are:
```
-db-address string
Address used to connect to the MySQL instance (default "localhost:3306")
-db-name string
Name of the database with the asset information in the MySQL instance (default "fleet")
-db-password string
Password used to connect to the MySQL instance (default "insecure")
-db-user string
Username used to connect to the MySQL instance (default "fleet")
-dir string
Directory to put the exported assets
-key string
Key used to encrypt the assets
```

105
tools/mdm/assets/main.go Normal file
View file

@ -0,0 +1,105 @@
package main
import (
"context"
"database/sql"
"errors"
"flag"
"fmt"
"log"
"os"
"path/filepath"
"strings"
"github.com/WatchBeam/clock"
"github.com/fleetdm/fleet/v4/server/config"
"github.com/fleetdm/fleet/v4/server/datastore/mysql"
"github.com/fleetdm/fleet/v4/server/fleet"
)
const (
testUsername = "fleet"
testPassword = "insecure"
testAddress = "localhost:3306"
testDatabase = "fleet"
)
func main() {
flagKey := flag.String("key", "", "Key used to encrypt the assets")
flagDir := flag.String("dir", "", "Directory to put the exported assets")
flagDBUser := flag.String("db-user", testUsername, "Username used to connect to the MySQL instance")
flagDBPass := flag.String("db-password", testPassword, "Password used to connect to the MySQL instance")
flagDBAddress := flag.String("db-address", testAddress, "Address used to connect to the MySQL instance")
flagDBName := flag.String("db-name", testDatabase, "Name of the database with the asset information in the MySQL instance")
flag.Parse()
if *flagKey == "" {
log.Fatal("-key flag is required")
}
if *flagDir != "" {
if err := os.MkdirAll(*flagDir, os.ModePerm); err != nil {
log.Fatal("ensuring directory: ", err)
}
}
db, err := sql.Open(
"mysql",
fmt.Sprintf("%s:%s@tcp(%s)/?multiStatements=true", testUsername, testPassword, testAddress),
)
if err != nil {
log.Fatal("opening MySQL connection:", err)
}
defer db.Close()
mysqlCfg := config.MysqlConfig{
Username: *flagDBUser,
Password: *flagDBPass,
Address: *flagDBAddress,
Database: *flagDBName,
}
ds, err := mysql.New(
mysqlCfg,
clock.NewMockClock(),
mysql.LimitAttempts(1),
mysql.WithFleetConfig(&config.FleetConfig{
Server: config.ServerConfig{
PrivateKey: *flagKey,
},
}),
)
if err != nil {
log.Fatal("creating datastore instance:", err)
}
defer ds.Close()
ctx := context.Background()
assets, err := ds.GetAllMDMConfigAssetsByName(ctx, []fleet.MDMAssetName{
fleet.MDMAssetCACert,
fleet.MDMAssetCAKey,
fleet.MDMAssetAPNSKey,
fleet.MDMAssetAPNSCert,
fleet.MDMAssetABMCert,
fleet.MDMAssetABMKey,
fleet.MDMAssetABMToken,
fleet.MDMAssetSCEPChallenge,
})
if err != nil && !errors.Is(err, mysql.ErrPartialResult) {
log.Fatal("retrieving assets from db:", err)
}
for _, asset := range assets {
path := filepath.Join(*flagDir, string(asset.Name))
switch {
case strings.Contains(path, "_key"):
path = path + ".key"
case strings.Contains(path, "_cert"):
path = path + ".crt"
}
if err := os.WriteFile(path, asset.Value, 0600); err != nil {
log.Fatal("writing asset:", err)
}
log.Printf("wrote %s in %s", asset.Name, path)
}
}

View file

@ -58,9 +58,9 @@ setup () {
cp -r "$KEYS_SOURCE_DIRECTORY" "$KEYS_DIRECTORY"
if ! aws sts get-caller-identity &> /dev/null; then
prompt "You need to login to AWS using the cli, press any key to continue..."
prompt "You need to login to AWS using the cli."
aws sso login
prompt "AWS SSO login was successful, press any key to continue..."
prompt "AWS SSO login was successful."
fi
# GITHUB_TOKEN is only necessary when releasing to edge.
@ -71,9 +71,9 @@ setup () {
# We only need to be logged in to github when releasing to edge.
if [[ $ACTION == "release-to-edge" ]]; then
if ! gh auth status >/dev/null 2>&1; then
prompt "You need to login to Github using the cli, press any key to continue..."
prompt "You need to login to Github using the cli."
gh auth login
prompt "Github login was successful, press any key to continue..."
prompt "Github login was successful."
fi
fi
@ -97,7 +97,7 @@ setup () {
pull_from_remote () {
echo "Pulling repository from tuf.fleetctl.com... (--dryrun first)"
aws s3 sync s3://fleet-tuf-repo "$REPOSITORY_DIRECTORY" --exact-timestamps --dryrun
prompt "If the --dryrun looks good, press any key to continue... (no output means nothing to update)"
prompt "Check if the above --dry-run looks good (no output means nothing to update)."
aws s3 sync s3://fleet-tuf-repo "$REPOSITORY_DIRECTORY" --exact-timestamps
}
@ -157,7 +157,7 @@ release_fleetd_to_edge () {
BRANCH_NAME="release-fleetd-v$VERSION"
ORBIT_TAG="orbit-v$VERSION"
if [[ "$SKIP_PR_AND_TAG_PUSH" != "1" ]]; then
prompt "A PR for bumping the fleetd version will be created to trigger a Github Action that will build 'Fleet Desktop'. Press any key to continue..."
prompt "A PR will be created to trigger a Github Action to build desktop."
pushd "$GIT_REPOSITORY_DIRECTORY"
git checkout -b "$BRANCH_NAME"
make changelog-orbit version="$VERSION"
@ -166,10 +166,8 @@ release_fleetd_to_edge () {
git add .github/workflows/generate-desktop-targets.yml "$ORBIT_CHANGELOG"
git commit -m "Release fleetd $VERSION"
git push origin "$BRANCH_NAME"
prompt "A PR will be created, press any key to continue..."
gh pr create -f -B main -t "Release fleetd $VERSION"
prompt "Press any key to continue after the PR is created and you have made all the necessary edits to it..."
prompt "A 'git tag' will be created to trigger a Github Action to build orbit, press any key to continue..."
prompt "A 'git tag' will be created to trigger a Github Action to build orbit."
git tag "$ORBIT_TAG"
git push origin "$ORBIT_TAG"
popd
@ -202,7 +200,7 @@ release_fleetd_to_edge () {
release_osqueryd_to_edge () {
echo "Releasing osqueryd to edge..."
prompt "A branch and PR for bumping the osquery version will be created. Press any key to continue..."
prompt "A branch and PR for bumping the osquery version will be created."
BRANCH_NAME=release-osqueryd-v$VERSION
if [[ "$SKIP_PR_AND_TAG_PUSH" != "1" ]]; then
pushd "$GIT_REPOSITORY_DIRECTORY"
@ -211,8 +209,8 @@ release_osqueryd_to_edge () {
git add .github/workflows/generate-osqueryd-targets.yml
git commit -m "Bump osqueryd version to $VERSION"
git push origin "$BRANCH_NAME"
open "https://github.com/fleetdm/fleet/pull/new/$BRANCH_NAME"
prompt "Press any key to continue after the PR is created..."
prompt "A PR will be created to trigger a Github Action to build osqueryd."
gh pr create -f -B main -t "Release osqueryd $VERSION"
popd
fi
OSQUERYD_ARTIFACT_DOWNLOAD_DIRECTORY="$ARTIFACTS_DOWNLOAD_DIRECTORY/osqueryd"
@ -253,7 +251,7 @@ push_to_remote () {
aws s3 sync "$REPOSITORY_DIRECTORY" s3://fleet-tuf-repo --dryrun
if [[ $PUSH_TO_REMOTE == "1" ]]; then
echo "WARNING: This step will push the release to tuf.fleetctl.com (production)..."
prompt "If the --dryrun looks good, press any key to continue..."
prompt "Check if the above --dry-run looks good."
aws s3 sync "$REPOSITORY_DIRECTORY" s3://fleet-tuf-repo
echo "Release has been pushed!"
echo "NOTE: You might see some clients failing to upgrade due to some sha256 mismatches."
@ -265,7 +263,14 @@ push_to_remote () {
prompt () {
printf "%s\n" "$1"
read -r -s -n 1
printf "Type 'yes' to continue... "
while read -r word;
do
if [[ "$word" == "yes" ]]; then
printf "\n"
return
fi
done
}
setup_to_become_publisher () {
@ -279,7 +284,7 @@ setup_to_become_publisher () {
mkdir -p "$KEYS_DIRECTORY"
if ! aws sts get-caller-identity &> /dev/null; then
aws sso login
prompt "AWS SSO login was successful, press any key to continue..."
prompt "AWS SSO login was successful."
fi
# These need to be exported for use by `tuf` commands.
FLEET_TARGETS_PASSPHRASE=$(op read "op://$TARGETS_PASSPHRASE_1PASSWORD_PATH")
@ -306,15 +311,15 @@ fi
print_reminder () {
if [[ $ACTION == "release-to-edge" ]]; then
if [[ $COMPONENT == "fleetd" ]]; then
prompt "Make sure to install fleetd with '--orbit-channel=edge --desktop-channel=edge' on a Linux, Windows and macOS VM. (To smoke test the release.) Press any key to continue..."
prompt "Make sure to install fleetd with '--orbit-channel=edge --desktop-channel=edge' on a Linux, Windows and macOS VM. (To smoke test the release.)"
elif [[ $COMPONENT == "osqueryd" ]]; then
prompt "Make sure to install fleetd with '--osqueryd-channel=edge' on a Linux, Windows and macOS VM. (To smoke test the release.) Press any key to continue..."
prompt "Make sure to install fleetd with '--osqueryd-channel=edge' on a Linux, Windows and macOS VM. (To smoke test the release.)"
fi
elif [[ $ACTION == "promote-edge-to-stable" ]]; then
if [[ $COMPONENT == "fleetd" ]]; then
prompt "Make sure to install fleetd with '--orbit-channel=stable --desktop-channel=stable' on a Linux, Windows and macOS VM. (To smoke test the release.) Press any key to continue..."
prompt "Make sure to install fleetd with '--orbit-channel=stable --desktop-channel=stable' on a Linux, Windows and macOS VM. (To smoke test the release.)"
elif [[ $COMPONENT == "osqueryd" ]]; then
prompt "Make sure to install fleetd with '--osqueryd-channel=stable' on a Linux, Windows and macOS VM. (To smoke test the release.) Press any key to continue..."
prompt "Make sure to install fleetd with '--osqueryd-channel=stable' on a Linux, Windows and macOS VM. (To smoke test the release.)"
fi
else
echo "Unsupported action: $ACTION"

View file

@ -163,19 +163,22 @@ func byteCountSI(b int64) string {
func channelVersionCommand() *cli.Command {
componentFileMap := map[string]map[string]string{
"orbit": {
"linux": "orbit",
"macos": "orbit",
"windows": "orbit.exe",
"linux": "orbit",
"linux-arm64": "orbit",
"macos": "orbit",
"windows": "orbit.exe",
},
"desktop": {
"linux": "desktop.tar.gz",
"macos": "desktop.app.tar.gz",
"windows": "fleet-desktop.exe",
"linux": "desktop.tar.gz",
"linux-arm64": "desktop.tar.gz",
"macos": "desktop.app.tar.gz",
"windows": "fleet-desktop.exe",
},
"osqueryd": {
"linux": "osqueryd",
"macos-app": "osqueryd.app.tar.gz",
"windows": "osqueryd.exe",
"linux": "osqueryd",
"linux-arm64": "osqueryd",
"macos-app": "osqueryd.app.tar.gz",
"windows": "osqueryd.exe",
},
"nudge": {
"macos": "nudge.app.tar.gz",
@ -305,7 +308,7 @@ func channelVersionCommand() *cli.Command {
fmt.Printf("%s\n", b)
} else if format == "markdown" {
table := tablewriter.NewWriter(os.Stdout)
table.SetHeader([]string{"Component\\OS", "macOS", "Linux", "Windows"})
table.SetHeader([]string{"Component\\OS", "macOS", "Linux", "Windows", "Linux (arm64)"})
table.SetAutoFormatHeaders(false)
table.SetCenterSeparator("|")
table.SetHeaderLine(true)
@ -332,7 +335,7 @@ func channelVersionCommand() *cli.Command {
for _, component := range componentsInOrder {
oss := outputMap[component]
row := []string{component}
for _, os := range []string{"macos", "linux", "windows"} {
for _, os := range []string{"macos", "linux", "windows", "linux-arm64"} {
row = append(row, setIfEmpty(oss, os))
}
rows = append(rows, row)