Skip to content

Commit b986033

Browse files
committed
Merge branch 'main' into 42290-wipe-activity
2 parents 803a25d + 28473e7 commit b986033

347 files changed

Lines changed: 9947 additions & 2914 deletions

File tree

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

.github/workflows/loadtest-osquery-perf.yml

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,7 @@ on:
1313
default: "main"
1414
required: true
1515
loadtest_containers:
16-
description: "Deploys osquery-perf containers all at once. Total number of osquery-perf tasks to run (should be a multiple of 8, if setting loadtest_containers_starting_index). This is also used as the end index in enroll.sh"
16+
description: "Deploys osquery-perf containers all at once. Total number of osquery-perf tasks to run. This is also used as the end index in enroll.sh"
1717
type: string
1818
required: true
1919
loadtest_containers_starting_index:
@@ -22,7 +22,7 @@ on:
2222
default: 0
2323
required: true
2424
task_size:
25-
description: "CPU and Memory setting for osquery-perf containers. Example: {\"cpu\":\"4098\",\"memory\":\"8192\"}"
25+
description: "CPU and Memory setting for osquery-perf containers. Example: {\"cpu\":\"4096\",\"memory\":\"8192\"}"
2626
type: string
2727
default: "{\"cpu\":\"4096\",\"memory\":\"8192\"}"
2828
required: true

.github/workflows/test-packaging.yml

Lines changed: 0 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -84,16 +84,6 @@ jobs:
8484
with:
8585
go-version-file: "go.mod"
8686

87-
- name: Install wine and wix
88-
if: startsWith(matrix.os, 'macos')
89-
run: |
90-
./assets/scripts/install-wine.sh -n
91-
wget https://github.com/wixtoolset/wix3/releases/download/wix3112rtm/wix311-binaries.zip -nv -O wix.zip
92-
mkdir wix
93-
unzip wix.zip -d wix
94-
rm -f wix.zip
95-
echo wix installed at $(pwd)/wix
96-
9787
- name: Build fleetctl
9888
run: make fleetctl
9989

@@ -128,7 +118,3 @@ jobs:
128118

129119
- name: Build PKG with Fleet Desktop
130120
run: ./build/fleetctl package --type pkg --enroll-secret=foo --fleet-url=https://localhost:8080 --fleet-desktop
131-
132-
- name: Build MSI on macOS (using local Wix)
133-
if: startsWith(matrix.os, 'macos')
134-
run: ./build/fleetctl package --type msi --enroll-secret=foo --fleet-url=https://localhost:8080 --fleet-desktop --local-wix-dir ./wix

Dockerfile-desktop-linux

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
FROM --platform=linux/amd64 golang:1.26.1-trixie@sha256:96b28783b99bcd265fbfe0b36a3ac6462416ce6bf1feac85d4c4ff533cbaa473
1+
FROM --platform=linux/amd64 golang:1.26.2-trixie@sha256:b53c282df83967299380adbd6a2dc67e750a58217f39285d6240f6f80b19eaad
22
LABEL maintainer="Fleet Developers"
33

44
RUN apt-get update && apt-get install -y musl-tools && rm -rf /var/lib/apt/lists/*

Makefile

Lines changed: 62 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -680,12 +680,62 @@ restore: $(SNAPSHOT_BINARY)
680680
# Generate osqueryd.app.tar.gz bundle from osquery.io.
681681
#
682682
# Usage:
683+
# To generate an osquery bundle for a released version of osquery:
683684
# make osqueryd-app-tar-gz version=5.1.0 out-path=.
685+
#
686+
# To generate an osquery bundle for a unreleased change in osquery in a pull request
687+
# (e.g. https://github.com/osquery/osquery/pull/8815):
688+
# make osqueryd-app-tar-gz pr=8815 out-path=.
684689
osqueryd-app-tar-gz:
685690
ifneq ($(shell uname), Darwin)
686691
@echo "Makefile target osqueryd-app-tar-gz is only supported on macOS"
687692
@exit 1
688693
endif
694+
ifdef pr
695+
$(eval TMP_DIR := $(shell mktemp -d))
696+
@echo "Fetching macos_unsigned_tgz_universal artifact from osquery/osquery PR $(pr)..."
697+
@PR_SHA=$$(gh pr view -R osquery/osquery $(pr) --json headRefOid -q .headRefOid) && \
698+
echo "PR head SHA: $$PR_SHA" && \
699+
RUN_IDS=$$(gh api "repos/osquery/osquery/actions/runs?head_sha=$$PR_SHA" \
700+
-q '[.workflow_runs[] | select(.conclusion == "success") | .id] | .[]') && \
701+
if [ -z "$$RUN_IDS" ]; then \
702+
echo "Error: no successful workflow runs found for PR $(pr)"; \
703+
rm -rf $(TMP_DIR); \
704+
exit 1; \
705+
fi && \
706+
DOWNLOADED=false && \
707+
for run_id in $$RUN_IDS; do \
708+
if gh run download -R osquery/osquery $$run_id -n macos_unsigned_tgz_universal -D $(TMP_DIR)/artifact 2>/dev/null; then \
709+
DOWNLOADED=true; \
710+
echo "Downloaded artifact from run $$run_id"; \
711+
break; \
712+
fi; \
713+
done && \
714+
if [ "$$DOWNLOADED" != "true" ]; then \
715+
echo "Error: macos_unsigned_tgz_universal artifact not found in any successful run for PR $(pr)"; \
716+
rm -rf $(TMP_DIR); \
717+
exit 1; \
718+
fi
719+
@INNER_TGZ=$$(find $(TMP_DIR)/artifact -name '*.tar.gz' -o -name '*.tgz' | head -1) && \
720+
if [ -z "$$INNER_TGZ" ]; then \
721+
echo "Error: no tarball found inside downloaded artifact"; \
722+
rm -rf $(TMP_DIR); \
723+
exit 1; \
724+
fi && \
725+
mkdir -p $(TMP_DIR)/extracted && \
726+
tar xf "$$INNER_TGZ" -C $(TMP_DIR)/extracted
727+
@OSQUERY_APP=$$(find $(TMP_DIR)/extracted -type d -name 'osquery.app' | head -1) && \
728+
if [ -z "$$OSQUERY_APP" ]; then \
729+
echo "Error: osquery.app not found in extracted artifact. Contents:"; \
730+
find $(TMP_DIR)/extracted -type f; \
731+
rm -rf $(TMP_DIR); \
732+
exit 1; \
733+
fi && \
734+
OSQUERY_APP_DIR=$$(dirname "$$OSQUERY_APP") && \
735+
"$$OSQUERY_APP/Contents/MacOS/osqueryd" --version && \
736+
tar czf $(out-path)/osqueryd.app.tar.gz -C "$$OSQUERY_APP_DIR" osquery.app
737+
rm -rf $(TMP_DIR)
738+
else
689739
$(eval TMP_DIR := $(shell mktemp -d))
690740
curl -L https://github.com/osquery/osquery/releases/download/$(version)/osquery-$(version).pkg --output $(TMP_DIR)/osquery-$(version).pkg
691741
pkgutil --expand $(TMP_DIR)/osquery-$(version).pkg $(TMP_DIR)/osquery_pkg_expanded
@@ -695,6 +745,7 @@ endif
695745
$(TMP_DIR)/osquery_pkg_payload_expanded/opt/osquery/lib/osquery.app/Contents/MacOS/osqueryd --version
696746
tar czf $(out-path)/osqueryd.app.tar.gz -C $(TMP_DIR)/osquery_pkg_payload_expanded/opt/osquery/lib osquery.app
697747
rm -r $(TMP_DIR)
748+
endif
698749

699750
# Generate nudge.app.tar.gz bundle from nudge repo.
700751
#
@@ -889,7 +940,17 @@ vex-report:
889940

890941
# make update-go version=1.24.4
891942
UPDATE_GO_DOCKERFILES := ./Dockerfile-desktop-linux ./infrastructure/loadtesting/terraform/docker/loadtest.Dockerfile ./tools/mdm/migration/mdmproxy/Dockerfile
892-
UPDATE_GO_MODS := go.mod ./tools/mdm/windows/bitlocker/go.mod ./tools/snapshot/go.mod ./tools/terraform/go.mod
943+
UPDATE_GO_MODS := \
944+
go.mod \
945+
./tools/mdm/windows/bitlocker/go.mod \
946+
./tools/snapshot/go.mod \
947+
./tools/terraform/go.mod \
948+
./third_party/vuln-check/go.mod \
949+
./tools/ci/setboolcheck/go.mod \
950+
./tools/github-manage/go.mod \
951+
./tools/qacheck/go.mod \
952+
./third_party/goval-dictionary/go.mod \
953+
./tools/fleet-mcp/go.mod
893954
update-go:
894955
@test $(version) || (echo "Mising 'version' argument, usage: 'make update-go version=1.24.4'" ; exit 1)
895956
@for dockerfile in $(UPDATE_GO_DOCKERFILES) ; do \

android/app/src/main/java/com/fleetdm/agent/ApiClient.kt

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,7 @@ import kotlinx.coroutines.flow.map
2222
import kotlinx.coroutines.sync.Mutex
2323
import kotlinx.coroutines.sync.withLock
2424
import kotlinx.coroutines.withContext
25+
import kotlinx.serialization.EncodeDefault
2526
import kotlinx.serialization.KSerializer
2627
import kotlinx.serialization.SerialName
2728
import kotlinx.serialization.Serializable
@@ -438,6 +439,9 @@ object ApiClient : CertificateApiClient {
438439
)
439440
}
440441

442+
// @EncodeDefault is marked @ExperimentalSerializationApi, but it has shipped in kotlinx.serialization since 1.3 (2022)
443+
// and is widely used and reliable in production. The opt-in only acknowledges that the API shape could change in a future version.
444+
@OptIn(kotlinx.serialization.ExperimentalSerializationApi::class)
441445
@Serializable
442446
data class EnrollRequest(
443447
@SerialName("enroll_secret")
@@ -446,6 +450,7 @@ data class EnrollRequest(
446450
val hardwareUUID: String,
447451
@SerialName("hardware_serial")
448452
val hardwareSerial: String,
453+
@EncodeDefault(EncodeDefault.Mode.ALWAYS)
449454
@SerialName("platform")
450455
val platform: String = "android",
451456
@SerialName("computer_name")

android/app/src/test/java/com/fleetdm/agent/ApiClientReenrollTest.kt

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -100,10 +100,15 @@ class ApiClientReenrollTest {
100100
assertTrue("First call should succeed", firstResult.isSuccess)
101101
assertEquals(2, mockWebServer.requestCount) // enroll + config
102102

103-
// Verify first enrollment used the enroll secret
103+
// Verify first enrollment used the enroll secret and sent platform="android" on the wire
104104
val firstEnroll = mockWebServer.takeRequest()
105105
assertEquals("/api/fleet/orbit/enroll", firstEnroll.path)
106-
assertTrue(firstEnroll.body.readUtf8().contains("test-enroll-secret"))
106+
val firstEnrollBody = firstEnroll.body.readUtf8()
107+
assertTrue(firstEnrollBody.contains("test-enroll-secret"))
108+
assertTrue(
109+
"Expected platform=\"android\" in enroll body, got: $firstEnrollBody",
110+
firstEnrollBody.contains("\"platform\":\"android\""),
111+
)
107112

108113
// Verify first config used first-node-key
109114
val firstConfig = mockWebServer.takeRequest()
Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
- Fixed Android agent to always send the `platform` field on enrollment so the device is registered with the correct platform.
Lines changed: 54 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,54 @@
1+
### Linux adoption is growing. Management hasn't kept up.
2+
3+
* macOS and Windows have mature management ecosystems. Linux does not.
4+
* Compliance frameworks don't grant exemptions by operating system.
5+
* Security audits don't skip Linux workstations.
6+
* These create the Linux gap.
7+
8+
### Unmanaged devices are unmanaged risk.
9+
10+
This guide helps IT leaders understand and close the Linux management gap.
11+
12+
### What you'll learn
13+
14+
You'll learn about a maturity model for planning your adoption path, a clear framework for defining your requirements, and a concrete evaluation scorecard for comparing management platforms. Whether you manage 50 Linux workstations or 5,000, this guide gives you the structure to make a defensible platform decision and explain it to your team.
15+
16+
### Chapter list
17+
18+
- **Why Linux devices are important**
19+
* What's driving enterprise Linux adoption and why management is no longer optional.
20+
- **The business case for managing Linux devices**
21+
* Cost, compliance, talent retention, and the price of inaction.
22+
- **Defining your Linux device management needs**
23+
* Key questions to ask and a maturity model to map your goals.
24+
- **Automated provisioning for Linux desktop in the enterprise**
25+
* The provisioning gap, enrollment approaches, and what zero-touch looks like on Linux.
26+
- **Security baselines for Linux**
27+
* Why baselines matter, what to enforce, and how to fight configuration drift.
28+
- **App and certificate management for Linux**
29+
* Software distribution challenges, the notarization gap, patching speed, and shrinking certificate lifetimes.
30+
- **Protecting the Linux device**
31+
* USB and Bluetooth threats, the sudo problem, and remote lock and wipe.
32+
- **Controlling your software and your data**
33+
* Software sovereignty, data sovereignty, and why your management tooling should reflect the values that made Linux worth adopting.
34+
- **Choosing the right solution**
35+
* Business and technical requirements, an evaluation criteria table, and a structured way to compare platforms.
36+
37+
38+
39+
<meta name="articleTitle" value="The IT leader's guide to Linux device management">
40+
41+
<meta name="authorFullName" value="n/a">
42+
<meta name="authorGitHubUsername" value="fleet-release">
43+
44+
<meta name="category" value="whitepaper">
45+
<meta name="publishedOn" value="2026-04-20">
46+
<meta name="description" value="Close the Linux management gap. A guide to help IT leaders understand the business case, security, compliance, and choosing the right solution.">
47+
48+
49+
<meta name="articleImageUrl" value="../website/assets/images/articles/IT-leaders-guide-to-Linux-device-management-cover-image-504x336@2x.png">
50+
<meta name="whitepaperFilename" value="IT-leaders-guide-to-Linux-device-management.pdf">
51+
<meta name="formHeadline" value="Learn how to close the Linux management gap">
52+
53+
<meta name="introductionTextBlockOne" value="Linux now exceeds 5% of desktop market share. Stack Overflow's 2025 developer survey shows nearly 30% of developers use Linux as their primary work OS.">
54+
<meta name="introductionTextBlockTwo" value="Your most important contributors, developers, engineers, and security practitioners, are choosing Linux. And in most organizations, those devices sit outside formal IT management.">
Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
Join Brock Walters from Fleet and their customers for a candid conversation around enabling device management in the enterprise at the speed that business demands. Explore how to help your IT teams get out of the way by giving employees their time back, reducing spend, and proving compliance in real time.
2+
3+
## Why Modern Device Management Matters
4+
5+
This session will cover how to deliver configurations and updates that accelerate work, maintain real-time visibility that keeps IT audit-ready without last-minute scrambles, use live health data to catch issues before they become tickets, and respect end user focus with transparent device management.
6+
7+
### The GitOps Advantage
8+
9+
The sessions will also cover how a GitOps approach to using device management solutions eliminates manual "click-ops" and prevents configuration drift. Store changes live in a version-controlled workflow - peer-reviewed, transparent, and easy to roll back. Understand how your engineering talent can spend less time on repetitive tasks and more time on work that matters, at scale.
10+
11+
12+
13+
<meta name="articleTitle" value="Device management that actually works for IT">
14+
15+
<meta name="authorFullName" value="n/a">
16+
<meta name="authorGitHubUsername" value="fleet-release">
17+
18+
<meta name="category" value="webinar">
19+
<meta name="publishedOn" value="2026-04-21">
20+
<meta name="description" value="Explore how to help your IT teams get out of the way by giving employees their time back, reducing spend, and proving compliance in real time.">
21+
22+
<meta name="webinarEmbeddedVideoUrl" value="https://player.mediadelivery.net/play/637410/0ecc433a-fa3c-4ff9-a178-621d6da0847e">
23+
24+

articles/how-to-define-your-Linux-device-management-needs.md

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@ To do this, you will need sophisticated and flexible tools. But first, you need
1010

1111
In this article, we will discuss key questions to ask as you define your organizational goals for Linux device management. We will also discuss how these goals can be mapped to a maturity model of Linux MDM adoption. Formally defining your Linux needs and understanding your target location on this maturity model will help you adopt robust technical solutions for Linux MDM.
1212

13-
## Questions to Consider
13+
## Questions to consider
1414

1515
Every business is different, and every team has its own needs based on team dynamics, regulatory requirements, and other factors. However, you can set yourself up for success by asking a few common questions to understand your Linux device goals:
1616

@@ -92,13 +92,13 @@ IT teams are not monolithic. A helpdesk technician needs different access than a
9292

9393
Define your access control requirements before evaluating platforms. A tool that offers only administrator versus read-only access will create friction as your team grows or your compliance requirements become more specific. This is easy to overlook during a demo and painful to work around in production.
9494

95-
## The Linux MDM Maturity Model
95+
## The Linux MDM maturity model
9696

9797
Not every organization needs the same level of Linux device management. This model defines four levels, from basic monitoring to full zero-touch provisioning. Your requirements determine which level is right for you, and not every team needs to reach level 4\.
9898

9999
When planning, consider both short and long-term goals. A short-term goal might be to understand which software your Linux users are running. A long-term goal might be automatically provisioning the tools every engineer needs to do their job. Either way, start by knowing where you want to land before deciding how far to climb.
100100

101-
### Level 1 \- Monitoring and Auditing
101+
### Level 1 \- Monitoring and auditing
102102

103103
Providing device monitoring, reporting, and insight is the first level in the Linux device management maturity model. All teams need some level of device monitoring to ensure compliance with internal and external policies. You must understand your environment before you can manage it. Robust monitoring provides individual and aggregate metrics to drive intelligent decisions.
104104

@@ -110,21 +110,21 @@ Monitoring lets you answer questions like:
110110

111111
For some organizations, especially small teams with limited Linux footprints, this may be the final level on their journey. If you only have a handful of Linux workstations, then you may not need further device management features. However, everyone can benefit from understanding the state of their environment.
112112

113-
### Level 2 \- Security and System Baselines
113+
### Level 2 \- Security and system baselines
114114

115115
Equipped with a solid understanding of your Linux devices, you can begin providing baseline configurations that meet organizational and security policies.
116116

117117
Start with something simple, like implementing a specific security policy. For example, you may want to prevent users from adding any local accounts to their workstations. As you gain experience and user trust, you can move on to more advanced configurations that help your users. For example, you can deploy corporate certificates automatically on all of your Linux workstations.
118118

119119
Basic system management might be the final stop on your maturity journey. Many organizations are quite happy to provide baseline system management and leave the rest to their highly-skilled end users.
120120

121-
### Level 3 \- Self-Service Configuration and Software
121+
### Level 3 \- Self-service configuration and software
122122

123123
Linux users are technically skilled, and most are comfortable installing and managing their own software. But even advanced users who’ve been using Linux on their desktop for years still sigh when they have to install a complex package with custom configuration. This is toil, and Linux users often face the brunt of it due to a lack of robust MDM tooling.
124124

125125
This level in the maturity journey is all about providing your Linux users with access to the tools and software to do their job. Consider the complexity of even a simple package installation in a modern organization. A user may have to add an internal company repository, determine the correct version that matches production, install the software itself, and then configure it to match the organization’s preferred configs. Providing a self-service portal, such as [Fleet Desktop](https://fleetdm.com/guides/fleet-desktop), saves hours.
126126

127-
### Level 4 \- Zero-Touch Provisioning and Drift Management
127+
### Level 4 \- Zero-touch provisioning and drift management
128128

129129
Level 4 is full zero-touch provisioning and automated, continuous management of devices. A new Linux device can be powered on and immediately put into service by an end-user without any IT involvement (discussed in the next article). Organizations can onboard new Linux employees just as they do Windows and Mac users.
130130

0 commit comments

Comments
 (0)