· Careers

Technical Program Manager Role - Security & Privacy

Join our Security & Privacy TPM team to drive strategic initiatives that enhance operational efficiency and resilience across our security organization.

Join our Security & Privacy TPM team to drive strategic initiatives that enhance operational efficiency and resilience across our security organization.

Overview

We understand that modern enterprises need more than just security tools – they need strategic partners who can orchestrate comprehensive security programs while driving operational excellence. Our team of Technical Program Management (TPM) experts specializes in revolutionizing security operations for organizations ready to scale their security initiatives with precision and purpose.

Why Organizations Choose Us

Our clients partner with us because they recognize the need for security leadership that goes beyond traditional program management. We bring a unique blend of technical expertise and strategic vision to every engagement.

Our Security & Privacy TPM team acts as a force multiplier, collaborating with engineering and product teams to deliver impactful security solutions. We’re looking for candidates who combine:

  • Strong technical understanding of security domains
  • Strategic thinking and execution excellence
  • Outstanding stakeholder management skills
  • Data-driven approach to process improvement
  • Experience with identity/access management, cloud security, or related areas

Our Core Capabilities

Transform Security Operations

We don’t just manage programs – we transform them. Our TPM experts lead initiatives that enhance both the resilience and operational efficiency of your security organization. By implementing data-driven approaches and establishing clear metrics, we ensure your security operations deliver measurable results.

Technical Depth Required

We emphasize the “Technical” in Technical Program Manager. The ideal candidate brings:

Domain Expertise

Strong understanding of security fundamentals and ability to quickly grasp technical aspects across program lifecycles. Must be able to provide technical thought leadership while balancing strategic and execution responsibilities.

The Security & Privacy TPM Team

Our team acts as a force multiplier for the security organization, partnering with engineering and product teams to deliver high-impact, scalable security initiatives. We drive highly visible cross-functional programs requiring:

  • Technical thought leadership across engineering/product organizations
  • Collaboration with leaders to align security roadmaps with business goals
  • Engagement with stakeholders from senior leadership to developers
Key Qualifications
  • Proven track record leading through influence and driving change
  • Vision-setting and execution capabilities
  • Outstanding communication skills - able to articulate business impact and technical constraints
  • Strong prioritization and judgment skills
  • Ability to identify solution gaps and evaluate technical approaches
  • Data-driven approach to operational excellence
  • Background in IAM, cloud security, third party risk, or general security

Dark Mode

Dark Mode is triggered by the little ‘sunlight’ icon:in the page header. It is defined in the components/common/ToggleTheme.astro, but the event is attached and the action defined in components/common/BasicScripts.astro in the following snippet:

attachEvent('[data-aw-toggle-color-scheme]', 'click', function () {
  if (defaultTheme.endsWith(':only')) {
    return;
  }
  document.documentElement.classList.toggle('dark');
  localStorage.theme = document.documentElement.classList.contains('dark') ? 'dark' : 'light';
});

Note that this is a client event. BasicScripts.astro defines several other client-side functionality as well as this one.

Advanced Slot Usage

slots are part of the component implementation, which is a common concept among many frameworks, including Astrojs. The typical slot definition in a component looks like this:

---
// (file: MyComponent.astro)
const { title } = Astro.props;
export interface Props {
  title: string;
}
---

<div>
  <h2>{title}</h2>
  <slot />
  <!-- slot contents injected here -->
  <div></div>
</div>

And in usage elsewhere:

import MyComponent from "~/components/MyComponent"; ...
<MyComponent someArg="A Slot example">
  <p>This content will be displayed in the slot</p>
</MyComponent>

Alternate usage

There’s another way we can use slots, useful particularly when a component can have markdown content is as follows (study carefully…):

---
// (file: MyComponent.astro)

const { title } = Astro.props;
export interface Props {
  title: string;
}
const content: string = await Astro.props.render('default');
---

// renders the html to the 'content' variable
<div>
  <h2>{title}</h2>
  <div set:html={content} />
  <!-- slot contents injected here -->
  <div></div>
</div>

Whoa!! What’s going on here?

Notice there is no slot definition in the html portion of the component. Instead, what we do is have Astro render the slot content (here, the ‘default’ content, but you can also render named slots) into a variable, and then use that content in a div (for instance).

So, if the usage is in a markdown file, like so:

import MyComponent from '../../components/MyComponent';

# Using the above component in a .mdx file (that can take components)

{' '}

<MyComponent title="This is a slot implementor">### Here is some markdown content - With a bullet item.</MyComponent>

MyComponent renders the markdown to html and then injects it into the div.

This actually has a big advantage — consider that with the normal usage you don’t have access to the slot contents: Astro just plops the content into the <slot/> tag. Using this method, however, allows you to access the content and further manipulate it before it gets inserted into the html.

This allows a great deal of flexibility in component design.

Yet Another Step

Now, we get to the techniques used in AstroWind, we’ll use the pages/index.astro file to illustrate.

You’ll note that the index file imports a lot of components, each one roughly analagous to a panel in the index page. Each of these components, in turn, is instantiated sequentially throughout the page. But, you’ll notice that some of them use this kind of construct (we’ll use the last section, CallToAction, as it is most illustrative of the technique):

<CallToAction
  callToAction={{
    text: 'Get template',
    href: 'https://github.com/onwidget/astrowind',
    icon: 'tabler:download',
  }}
>
  <Fragment slot="title">
    Astro + <br class="block sm:hidden" /><span class="sm:whitespace-nowrap">Tailwind CSS</span>
  </Fragment>

  <Fragment slot="subtitle">
    Be very surprised by these huge fake numbers you are seeing on this page. <br class="hidden md:inline" />Don't waste
    more time! :P
  </Fragment>
</CallToAction>

Some things to note, here:

The callToAction argument

This argument is actually being passed a javascript object — not a string. (However, in the TS definition, it could be a string…)

There are several Fragment children

Furthermore, these <Fragment/> elements each have a slot=“(value)” specifier.

The latter seems odd, because <Fragment/> is a built-in component over which you have no control, and doesn’t have a provision for rendering slots, per se.

The answer lies in a paragraph in the Astro docs, slots section, which states:

Use a slot="my-slot" attribute on the child element that you want to pass through to a matching slot name="my-slot" /> placeholder in your component.

That’s pretty concise and a bit of a head-scratcher to read, but basically what it says is that:

  1. Given a component that defines a slot:
  2. you can reference a slot from a child element of that component and,
  3. provide content to the parent component’s slot from the child by naming the slot in the child with a slot="<slot-name>" property assignment, where the slot-name is the parent’s slot.

So, in the example above, the CallToAction component defines the subtitle slot, and the following <Fragment slot=“subtitle”> populates the slot with the following content:

<Fragment slot="subtitle">
  Be very surprised by these huge fake numbers you are seeing on this page. <br class="hidden md:inline" />Don't waste
  more time! :P
</Fragment>

And, the CallToAction component defines and renders it thusly:

---
//...
const { subtitle = await Astro.slots.render('subtitle') } = Astro.props;
---

//...
{subtitle && <p class="text-xl text-muted dark:text-slate-400" set:html={subtitle} />}
//...

There’s a lot to wrap your head around, here.

Notice first that subtitle is defined as a prop/argument, but it’s being processed as a slot. Interestingly, prop args and slots seem to be somewhat interchangeable: if the subtitle was just a string, it would simply take that assignment. The main difference is that if you render them independently, you have to call the render with an await modifier.

Back to Blog

Related Posts

View All Posts »