People Work

Overview

People Work exists to help managers and their engineering teams better manage the people side of their jobs. In short it helps a manager become a better manager and an employee better engage the performance management process.

Motivation

As a technical manager, you started your career in a technical capacity with lots of tools at your disposal, the loveliest and most used of which was your IDE of choice. I’m sure you can think of 3 or 4 tools off the top of your head that you used daily. Can you imagine having done your engineering job without them?

Then you became a manager, and suddenly the landscape of tooling was abysmal. You have the HR-approved tooling that you mostly just use to approve time off and submit performance reviews with. Beyond that, you probably just use Word or Google Docs to keep track of 1:1 notes for each of your direct reports. They’re such big files that you rarely go back and read anything because it’s really hard to find. Then when review time rolls around, you fall prey to the bias of the present. You talk about their last couple of projects and can’t remember anything that happened more than 6 weeks ago.

What if you had an IDE for managing your team? Just like during your technical days, you had an IDE to help you with best practices, like unit testing, builds, compiling, etc. What if you had an IDE to help you with 1:1s, reviews, feedback, and other performance related things? Think of how much more successful of a manager you would be for your team if you had a world-class tool helping you rather than a tool for someone else that makes you feel like you’re just checking off a box.

And what if this tool was so good that your technical team actually used it to engage in their own career growth, resulting in them being more engaged and more productive team members? Those types of teams and leaders are rare. We build the tooling to create those outcomes and make your journey as manager as short and upwardly mobile as possible.

You may think of this as a typically HR tool, and you're right - it is! But we are here to partner with HR in order to enable managers and employees to do better at managing relationships in order for HR to manage more strategic outcomes.

Installation

To run the application, pull the code, run just cs, and run the code in XCode.

macOS Configuration

If you want to navigate our forms via the keyboard through tabbing, you should configure your System Settings:

  1. Open up System Settings on your Mac
  2. Search for "Mission Control" and click on "Keyboard and Mouse Shortcuts" on the left
  3. In the "Keyboard Navigation" section on the right, click on "Keyboard Shortcuts"
  4. Ensure the "Keyboard Navigation" tab is on system settings

Overview

This app creates an operating system for working with others. Just as in a computer's operating system you have processes for things like managing files and applications, in this operating system we provide an opinionated framework of processes to navigate complex human people systems.

These processes are divided into three sections:

  1. Get Control Of Your Time - Segment, Plan, Track
  2. Manage Performance - Assess, Align, Track
  3. Onboard Your Team

Get Control Of Your Time

flowchart LR
    A[Segment]:::teal --> B[Plan]:::teal
    B[Plan] --> C[Track]:::teal
    
    classDef teal fill:#000000,stroke:#66cccc,color:white

Getting control of your time is foundational in People Work. The exercise of segmenting, planning, and tracking the professional relationships that are most impactful to your career will allow you to maximize your effectiveness and really enjoy the connections along the way.

Below are some questions you'll need to be ready to answer while you onboard yourself to People Work.

Segment

Who are your people? This list should be purposeful and precise, not a catch-all. Make a list of all the people that fit into the following categories:

  • Direct Reports - those that report to you or are looking to you for leadership
  • First Team - those who report to your same boss or are peer to you and share your same objectives
  • Stakeholders - those with a vested interest in your outcomes — mentors, leadership, project stakeholders
  • Base - these connections are less frequent but still meaningful professional relationships who help you maintain broader influence beyond your immediate sphere

Plan

Think about your intentional support of and from each person. How often should you meet in order to achieve this mutual support?

Track

Each relationship requires us to remember so much! What are the needs of each relationship that you will use People Work to help you keep track of? How is the health of each of these connections currently?

Manage Performance

Note

The term "manager" in this document is used generically to reference anyone managing performance, whether that be of a direct report or your own.

Whether you're managing others or yourself, you can effectively manage performance within three phases:

Align

First, align on expectations. The employee is assigned a job in the system, and those jobs have expectations that fit within a Career Matrix.

These expectations for the employee's job help the manager get clear with the employee about what the employee is being measured on.

The manager also sets an expectation with the employee of their intention for how often to check in.

Track

The manager and employee then both track what happens and how it relates to their performance, via a journal of connections. This ultimately creates evidence for the next conversation.

Assess

Now that expectations are set via alignment and evidence is gathered for how the employee met those expectations, it's time to assess performance.

The manager is able to review the journal and come up with an assessment.

Performance Management Process

Onboard Your Team

Just in the same way that managers are able to use People Work to manage their teams, individual contributors can use People Work to track their own performance and goals.

With a system in place for relationships and performance, it’s now time to scale that to others; first with your team and then with your broader organization.

flowchart LR
    A[Onboard]:::teal --> B[Share]:::teal
    B[Share] --> C[Report]:::teal
    
    classDef teal fill:#000000,stroke:#66cccc,color:white

Onboard

There are two ways you can invite someone to your workspace:

  • Share a workspace template with others who can quickly get started without having to enter in basic information for people, jobs, career matrices, or values, all while maintaining your privacy as well as theirs.

  • Automatically onboard to a shared service, which provides this information for you (coming soon).

Share

While privacy is a core value of People Work, there is some sharing that is necessary for growth and convenience. Those are noted here:

  • You are encouraged to share your workspace data with others.
  • You can share your workspace context, the files within your workspace directory, with AI in order to gain insights and see patterns.

Report

As more and more teams begin to use People Work and more senior leadership views the app, you can create spreadsheets from the data so that they can see things like:

  • Aggregate and specific details of how managers rate their employees and where there is a delta
  • Timeline of aggregated details over time, for example calibration, to see if managers are engaged

Workspaces

Workspaces are the fundamental grouping, or tenant, used in the app. A workspace is located within a folder that fits a very specific structure outlined in the dsl section below.

You can use a workspace in any way you like, but we recommend keeping it simple and doing one for work and perhaps one for your professional network outside of work.

When sharing a workspace, the following items are shared:

  • Assets such as avatar images
  • Members (but not the users' contacts)
  • Career Matrices + Jobs
  • Company Values (coming soon)

Onboarding

When you first open the People Work app, you will see a screen like this:

onboarding screen

If you have a shared workspace from another member of your organization, then you will click "Open Existing Workspace..." and navigate to that workspace.

If you are creating a new workspace, then you will see a form to create a new workspace when you click on "Create New Workspace...". Here is an example of a filled out form:

create a new workspace

Once you save, you will see an empty workspace with only your workspace in it.

empty workspace

Once you have added all of the contacts that wish to add (see Segment) via the UI or the contact in the DSL, you will see all of your contacts in your workspace like so:

populated workspace

You're now ready to start using the app!

DSL Overview

This section outlines our custom domain specific language for the application.

Motivation

We started developing these features in a much more conventional way, as a web application connected to a SQL database. As we used the app, we felt something was missing:

  1. Ownership - For true growth to happen, we know that honesty and vulnerability are key, two things that we feel strongly about enabling in our app. We wanted our users to feel safe to share about their private goals and sensitive work relationships in our app, and in order to better facilitate that, we wanted to let our users own their own data, not for it to be in the cloud where someone else had control over it.
  2. Visibility - We wanted the user to know exactly what the app was storing, no hidden data that they couldn't control.
  3. Insights - We want AI to be able to easily read and comment on the data but in a way that the user can control.

This DSL is our answer to those problems. It enables a private, locally stored database that is human readable and, with a bit of training, human writable.

Once onboarded, a user can choose to only interact with their workspace through the desktop application, however, the DSL will remain at the core.

Workspaces

At the core of our DSL is a workspace, which is a logical group of people that the user can relate to. Most people will have a workspace for their place of employment. But other people may choose to track their professional relationships outside of work and in other areas as well.

Workspace Structure

Workspaces are structured by convention:

  1. ./core.ppl contains the core, shareable concepts that make up the workspace, like members, jobs, and matrices. This is meant to be shareable with others in that same organization, to help them get started faster.
  2. ./people.ppl contains the user-specific connection to the core. Here declares themselves as the user and determines who their contacts are.They also set an intention for how to connect with each.
  3. ./work this is where the user tracks their work for themselves and each of their contacts. This is in the form of journaling connections
  4. ./assets this is where files are stored that the workspace relates to.

Console App

We provide the people command line application in order to help you work with a workspace without having to open the full app. There are two commands to use:

people init

Will set up a new workspace.

people check

Will ensure that a workspace is valid.

This tool is self documenting so run:

people

To learn about all the options.

Visual Studio Code Extension

We also provide a Visual Studio Code Extension for this DSL, which provides syntax highlighting.

Core

The core is stored in ./core.ppl. It is the part of the workspace that could easily be shared with other people in their organization, therefore it does not contain any private or user-specific data in it. The core consists of members, jobs, and matrices.

Member

A member is a part of the core and stored in ./core.ppl of the workspace. It tracks the basic and widely available information for a person or employee within an organization. A member also has an avatar which is stored by their id.

Fields

  • first_name - (Required) The first name of the person - String
  • last_name - (Required) The last name of the person - String
  • job - (Optional) The identifier of the job the person has, in order track their performance or as an optional reference. - Identifier
  • email - (Optional) The person's email - String

Examples

Minimal

member alex_rivera {
  first_name: "Alex"
  last_name: "Rivera"
}

Full

// avatar stored at ./assets/avatars/tara_johnson.jpg
member tara_johnson {
  first_name: "Tara"
  last_name: "Johnson"
  email: "tara@somecorp.com"
  job: principal_software_engineer
}

Job

A job is a part of the core and stored in ./core.ppl of the workspace. It tracks the basic requirements for a position within an organization, primarily for performance management purposes. It also defines requirements within the career matrix.

Fields

The following arguments are supported:

  • name - (Required) The human-readable name of the job - String
  • requirements - (Optional) A map of requirements by category for this job. See the career matrix topic for a full description. This field's properties are dependent on what is defined there.

Examples

Minimal

// since there are no requirements, there should be no career matrix either.
job manager {
  name: "Engineering Manager"
}

member alex_rivera {
  first_name: "Alex"
  last_name: "Rivera"
  job: manager
}

Full

job software_engineer_1 {
  name: "Software Engineer I"
  requirements: {
    technical: {
      implementation: "Implements well-defined features with guidance"
      code_quality: "Writes maintainable code following team standards"
      code_review: "Participates in code reviews and bug fixes"
      testing: "Learns testing best practices"
    }
    project_execution: {
      delivery: "Delivers assigned tasks within expected timeframes"
      clarity: "Seeks clarification when requirements are unclear"
      updates: "Updates progress regularly"
      process: "Follows established development processes"
    }
    problem_solving: {
      debugging: "Debugs and resolves basic technical issues"
      impact: "Understands how their code impacts immediate dependencies"
      decomposition: "Learns to break down problems into manageable tasks"
    }
    collaboration: {
      participation: "Actively participates in team meetings"
      communication: "Communicates blockers and progress clearly"
      feedback: "Receives and implements feedback effectively"
      teamwork: "Works well with immediate team members"
    }
    growth: {
      learning: "Demonstrates eagerness to learn new technologies"
      initiative: "Takes initiative in skill development"
      mentorship: "Seeks and accepts mentorship"
      domain: "Builds understanding of product domain"
    }
  }
}

matrix software_engineering {
  name: "Software Engineering"
  categories: {
    technical: {
      name: "Technical"
      description: "Core technical and architectural capabilities"
    }
    project_execution: {
      name: "Project Execution" 
      description: "Delivery and implementation of technical work"
    }
    problem_solving: {
      name: "Problem Solving"
      description: "Technical problem solving and system thinking"
    }
    collaboration: {
      name: "Collaboration"
      description: "Working with others and leadership"
    }
    growth: {
      name: "Growth and Learning"
      description: "Personal and professional development"
    }
  }
  jobs: [
    software_engineer_1,
  ]
}

member kevin_osei {
  first_name: "Kevin"
  last_name: "Osei"
  job: software_engineer_1
}

Matrix

A career matrix is a part of the core and stored in ./core.ppl of the workspace. It tracks the structure of requirements for a family of jobs in order to create clear career progression.

Fields

  • name - (Required) - The human-readable name of the matrix - String
  • categories - (Required) - A map of categories (detailed below) mapped by their category identifier, which is also used by the job requirments configuration
  • jobs - (Required) - A list of job identifiers that are a part of the career matrix. - [Identifier]

A category block is defined within the categories block. It defines a single category of job requirements for each job in this matrix. It is identified by a unique identifier within the matrix that is used to define the job requirements. Each category has its own block.

  • name - A human readable name of the category - String
  • description - A human readable description of the types of requirements in this category - String

Categories and Job Requirements

Career matrices and jobs have a structural relationship with each other when defined together.

The matrix defines categories, and the identifier of each category (technical in the minimal example below) is also defined as a requirement for the job.

If this structure isn't exactly right, the workspace will fail to load, so someone configuring a matrix with jobs should make good use of the people app.

Examples

Minimal

matrix engineering {
  name: "Software Engineering"
  categories: {
    technical: {
      name: "Technical"
      description: "Core technical and architectural capabilities"
    }
  }
  jobs: [
    software_engineer_1,
  ]
}

job software_engineer_1 {
  name: "Software Engineer I"
  requirements: {
    technical: {
      implementation: "Implements well-defined features with guidance"
    }
  }
}

member kevin_osei {
  first_name: "Kevin"
  last_name: "Osei"
  job: software_engineer_1
}

Full

job software_engineer_1 {
  name: "Software Engineer I"
  requirements: {
    technical: {
      implementation: "Implements well-defined features with guidance"
      code_quality: "Writes maintainable code following team standards"
      code_review: "Participates in code reviews and bug fixes"
      testing: "Learns testing best practices"
    }
    project_execution: {
      delivery: "Delivers assigned tasks within expected timeframes"
      clarity: "Seeks clarification when requirements are unclear"
      updates: "Updates progress regularly"
      process: "Follows established development processes"
    }
    problem_solving: {
      debugging: "Debugs and resolves basic technical issues"
      impact: "Understands how their code impacts immediate dependencies"
      decomposition: "Learns to break down problems into manageable tasks"
    }
    collaboration: {
      participation: "Actively participates in team meetings"
      communication: "Communicates blockers and progress clearly"
      feedback: "Receives and implements feedback effectively"
      teamwork: "Works well with immediate team members"
    }
    growth: {
      learning: "Demonstrates eagerness to learn new technologies"
      initiative: "Takes initiative in skill development"
      mentorship: "Seeks and accepts mentorship"
      domain: "Builds understanding of product domain"
    }
  }
}

job software_engineer_2 {
  name: "Software Engineer II"
  requirements: {
    technical: {
      implementation: "Independently implements medium-sized features"
      design: "Designs straightforward technical solutions"
      code_review: "Provides thorough code reviews"
      documentation: "Contributes to technical documentation"
    }
    project_execution: {
      delivery: "Manages own deliverables reliably"
      decision_making: "Makes informed technical decisions"
      estimation: "Estimates work effort accurately"
      risk_management: "Identifies potential risks early"
    }
    problem_solving: {
      resolution: "Resolves complex issues independently"
      system_thinking: "Considers broader system impact"
      improvement: "Suggests process improvements"
      optimization: "Identifies optimization opportunities"
    }
    collaboration: {
      mentoring: "Mentors junior engineers informally"
      cross_team: "Communicates effectively across teams"
      technical_discussion: "Contributes constructively to technical discussions"
      status: "Provides clear status updates"
    }
    growth: {
      technical_growth: "Expands technical breadth"
      domain_expertise: "Develops domain expertise"
      feedback: "Proactively seeks feedback"
      strategy: "Understands product strategy"
    }
  }
}

job senior_engineer {
  name: "Senior Software Engineer"
  requirements: {
    technical: {
      implementation: "Designs and implements complex features"
      architecture: "Architects scalable solutions"
      leadership: "Provides technical leadership"
      best_practices: "Drives best practices adoption"
    }
    project_execution: {
      initiative: "Leads significant technical initiatives"
      technical_debt: "Balances technical debt with delivery"
      architecture: "Makes sound architectural decisions"
      quality: "Ensures quality of deliverables"
    }
    problem_solving: {
      challenges: "Solves ambiguous technical challenges"
      scaling: "Anticipates scaling problems"
      solutions: "Creates systemic solutions"
      processes: "Improves development processes"
    }
    collaboration: {
      mentoring: "Mentors other engineers actively"
      influence: "Influences technical decisions"
      leadership: "Drives technical discussions"
      cross_org: "Works effectively across organization"
    }
    growth: {
      leadership: "Develops leadership capabilities"
      perspective: "Broadens system perspective"
      industry: "Stays current with industry trends"
      vision: "Contributes to technical vision"
    }
  }
}

job staff_engineer {
  name: "Staff Software Engineer"
  requirements: {
    technical: {
      architecture: "Architects complex distributed systems"
      strategy: "Drives technical strategy across projects"
      oversight: "Provides technical oversight for critical initiatives"
      decisions: "Makes high-impact architectural decisions"
    }
    project_execution: {
      leadership: "Leads multi-team technical initiatives"
      roadmap: "Defines technical roadmaps"
      excellence: "Ensures technical excellence across projects"
      balance: "Balances business needs with technical concerns"
    }
    problem_solving: {
      challenges: "Solves organizational technical challenges"
      architecture: "Creates scalable system architectures"
      opportunities: "Identifies strategic technical opportunities"
      governance: "Develops technical governance"
    }
    collaboration: {
      influence: "Influences cross-team technical decisions"
      consensus: "Builds consensus across engineering groups"
      mentoring: "Mentors senior engineers"
      communication: "Communicates technical vision effectively"
    }
    growth: {
      innovation: "Drives technical innovation"
      culture: "Shapes engineering culture"
      industry: "Contributes to industry discussions"
      leadership: "Develops organizational leadership skills"
    }
  }
}

job principal_engineer {
  name: "Principal Software Engineer"
  requirements: {
    technical: {
      vision: "Defines technical vision for multiple products"
      strategy: "Creates multi-year technical strategies"
      innovation: "Drives innovation in core architectures"
      standards: "Establishes technical standards"
    }
    project_execution: {
      leadership: "Leads organization-wide technical initiatives"
      planning: "Drives strategic technical planning"
      impact: "Makes decisions affecting multiple teams"
      strategy: "Influences product strategy"
    }
    problem_solving: {
      challenges: "Solves complex organizational challenges"
      capabilities: "Creates new technical capabilities"
      opportunities: "Identifies strategic opportunities"
      practices: "Develops engineering best practices"
    }
    collaboration: {
      influence: "Influences organization direction"
      partnerships: "Builds strategic partnerships"
      mentoring: "Mentors technical leaders"
      representation: "Represents engineering organization"
    }
    growth: {
      practice: "Advances state of practice"
      knowledge: "Contributes to industry knowledge"
      leadership: "Develops future technical leaders"
      culture: "Shapes engineering culture"
    }
  }
}

matrix software_engineering {
  name: "Software Engineering"
  categories: {
    technical: {
      name: "Technical"
      description: "Core technical and architectural capabilities"
    }
    project_execution: {
      name: "Project Execution" 
      description: "Delivery and implementation of technical work"
    }
    problem_solving: {
      name: "Problem Solving"
      description: "Technical problem solving and system thinking"
    }
    collaboration: {
      name: "Collaboration"
      description: "Working with others and leadership"
    }
    growth: {
      name: "Growth and Learning"
      description: "Personal and professional development"
    }
  }
  jobs: [
    software_engineer_1,
    software_engineer_2,
    senior_engineer,
    staff_engineer,
    principal_engineer
  ]
}

member kevin_osei {
  first_name: "Kevin"
  last_name: "Osei"
  job: software_engineer_2
  email: "test-kevin-osei@hedge-ops.com"
}

member alex_rivera {
  first_name: "Alex"
  last_name: "Rivera"
  email: "test-alex-rivera@hedge-ops.com"
}

People

The people section of the DSL is stored in ./people.ppl and stores the user-specific data for the app. It is not meant to be shared among people in the organization.

In this app, the user defines which member they are via user declaration and which members they want to relate to as contacts.

Users also set an intention for each contact in order to remind them to connect regularly with people.

User

Located in ./people.ppl, this is the member associated with the user. It is associated by sharing the same id.

This exists so that the core can be shared and the user can still relate themselves to that core.

If a user is not defined, the workspace will not load.

Fields

  • intention - (Optional) An intention block representing how the user wants to connect with themselves - Intention

Examples

Minimal

member alex_rivera {
  first_name: "Alex"
  last_name: "Rivera"
}

// same id as alex_rivera member, which means that Alex is
// the first person of this workspace (aka the user).
// no fields defined so no braces required
user alex_rivera

Full

member tara_johnson {
  first_name: "Tara"
  last_name: "Johnson"
}

// tara wants to reflect on this organization alone once a week
user tara_johnson {
  intention: {
    event_name: "Weekly Reflection"
    recurrence: "FREQ=WEEKLY;INTERVAL=1;BYDAY=TU"
  }
}

Contact

Located in ./people.ppl, this is the member that the user relates with in order to achieve their goals within the organization. The contact is associated with the member by sharing the same id.

This exists so the core can be shared, different users can relate to different people.

Fields

  • relationship - (Required) What type of relationship this contact is. Choices include stakeholder, first_team, direct_report, and base - Identifier
  • intention - (Optional) An intention block - Intention

Relationships

This app is prescriptive in helping people identify important relationships within an organization, and thus categorizes contacts into four groups. These are not official HR titles, just categories:

  1. Stakeholder: people who need for the user to deliver in order to succeed and will therefore advocate for user when they are not in the room.
  2. First Team: usually the people who report to the user's boss, sharing in a broader mission than the user has. This team is important to track because in order to perform and grow, one has to be supportive and not competitive with their peers.
  3. Direct Report: people who either report to the user or whom the user is leading or mentoring, when an individual contributor. The user is likely responsible for the outcome of their work.
  4. Base: this is every other important relationship, meant to ensure that there is a wider impact than just the team.

Examples

Minimal

member kevin_osei {
  first_name: "Kevin"
  last_name: "Osei"
}

// same id as kevin_osei member, which means that Kevin is
// a person the user of this workspace is relating to.
contact kevin_osei {
  relationship: direct_report
}

Full

member jordan_kim {
  first_name: "Jordan"
  last_name: "Kim"
}

contact jordan_kim {
  relationship: direct_report
  intention: {
    event_name: "1:1"
    recurrence: "FREQ=WEEKLY;INTERVAL=1;BYDAY=FR"
  }
}

Intention

An intention is set by the user for themselves and their contacts in order to maintain consistent connection.

The intention is essentially to connect with that person and journal that connection.

This is a child of both the user and contact, but we will document the fields and show examples here:

Fields

  • event_name - (Required) The name of the event that the user wants to have with that person - String
  • recurrence - (Required) The recurrence rule of the event - String in RRule format

Examples

// alex wants to self reflect every Friday
user alex_rivera {
  intention: {
    event_name: "Weekly Reflection"
    recurrence: "FREQ=WEEKLY;INTERVAL=1;BYDAY=FR"
  }
}

// Alex wants to have a 1:1 with Kevin every Thursday
contact kevin_osei {
  relationship: direct_report
  intention: {
    event_name: "1:1"
    recurrence: "FREQ=WEEKLY;INTERVAL=1;BYDAY=TH"
  }
}

Work

The policy of the app is set up with the core and people apps, but now it's time to do the work!

Types of Work

File Format

Each unit of work is defined within a file with a .wrk extension, straightforward and extensible. The file's name is the id for that work.

Connections - Journaling

As the user connects with themselves or other contacts, they will journal those connections. This is located in ./work/[id]/journal where [id] is the identifier of the user or contact.

File Format

The file is saved as [YYYY-mm-dd]_[event_name_identifier].wrk where the first part is the date of the connection and the second part is the event name where spaces and other odd characters are converted into underscores.

Fields

  • event - (Required) A block which includes details of the event, detailed below.
  • observations - (Optional, unless sentiment and comments are present) The factual elements of the connection. This should be descriptive of just the facts. - String
  • sentiment - (Optional) How the user felt about the event. Choices include negative, neutral, or positive - Identifier
  • comments - (Optional) the textual reaction of the user, their feelings about the situation - String

event

  • name - (Required) The name of the event
  • date- (Required) The date the connection occurred - String in YYYY-MM-DD format
  • recurrence- (Optional) when this event repeats, detailed below

recurrence

  • starting - (Required) the date that the recurrence starts repeating - String in YYYY-MM-DD format
  • repeats- (Required) a recurrence string describing the schedule during which the event repeats.

repeats has two main sections:

  1. Frequency and Interval. When interval is 1, the number can be omitted. Examples: daily, weekly, monthly, yearly, every 2 weeks, every 3 days
  2. Predicate, which is specific to the type of frequency:

daily

For daily there is no predicate.

Examples:

  • daily
  • every 3 days

weekly

For weekly the predicate is the day of the week: on Friday, on Saturday and Sunday, on Monday, Wednesday and Friday. If this is missing, the system will assume that the schedule will repeat on the day of the week that the starting date falls on.

Examples:

  • weekly
  • every 2 weeks
  • every 2 weeks on Friday
  • every 4 weeks on Monday, Wednesday and Friday

monthly

For monthly the predicate can either list out the day of month or specify the position within the month that repeats.

For repeating on specific days of the month, list them out: 1st, 1st and 15th, 1st, 3rd and 10th. This is optional and if it's omitted the day of month is assumed to be the same day of month that the starting date falls on.

For repeating on the position within the month, use an ordinal expression, which has two parts: (1) The ordinal: first, second, third, fourth, fifth, next to last, last and the day specification, which is a day of the week (Sunday, Monday) or one of day, weekday, or weekend day.

Examples:

Specific days of the month:

  • monthly on the 1st and 15th
  • every 2 months on the 1st

Position within the month:

  • monthly on the first Sunday
  • monthly on the last day
  • every 3 months on the first Friday

yearly

For yearly the predicate lists out the months as above, with in as a preposition: in January, in January and February, in January, February and March. Just as above, if the month is not there the system assumes that the month is the same month the starting date falls within.

The yearly also can have the ordinal predicate, as specified above.

Examples:

  • yearly
  • yearly in January
  • yearly in May and November
  • yearly on the last Sunday
  • yearly in May on the last day
  • every 3 years
  • every 4 years on the first Tuesday

Examples

Upcoming

// located in ./work/tara_johnson/journal/2025-01-23_lunch.wrk
// Alex (the user) will have lunch with Tara on January 23, 2025.
// After the lunch he'll come back and write his observations and reactions
// about the upcoming connection.
event: {
  name: "Lunch"
  date: "2025-01-23"
}

Recurring

event: {
  name: "Lunch"
  date: "2025-01-23"
  recurring: {
    starting: "2025-01-23"
    repeats: "every 2 weeks"
  }
}

Journaled

// located in ./work/tara_johnson/journal/2025-01-23_lunch.wrk
// Alex (the user) had lunch with Tara on January 23, 2025.
// He wrote down the important facts of their interaction
// He also wrote down his feelings about the ineraction
event: {
  name: "Lunch"
  date: "2025-01-23"
}
observations: """
Talked about Project Gravy which is late
Tara has helped Kevin deliver on the containers feature.
"""
sentiment: positive
comments: """
Tara does struggle with some things but I'm impressed by her being
a team player, especially with Kevin.
"""

Workspace Template

Once someone in your organization has created a workspace, there's no need to create a new one from scratch. You can share it with others in order to reuse shared concepts. Here's how you can do that:

  1. The new user will create a new nested folder on their computer called people/<workspace-name>, for example people/wincorp.

    Note

    The workspace folder is nested inside the people folder because if the user decides to create any new workspaces, they will create it inside this people folder.

  2. You, the original workspace creator, will copy your core.ppl file and assets folder with everything in it from your workspace folder and share it with them.

    Warning

    Ensure that your people.ppl file and your work folder is NOT included. These include your private entries that you will not want to share.

  3. The new user will put the shared core.ppl file and assets/* folder and contents in their newly created people folder on their computer.

  4. This new user will find the member associated with them in the core.ppl and copy their member ID. For example, if Kevin Osei was creating a user for himself, he would find this block in core.ppl and copy kevin_osei:

    member kevin_osei {
      first_name: "Kevin"
      last_name: "Osei"
      job: software_engineer_2
      email: "test-kevin-osei@wincorp.com"
    }
    
  5. The new user will then create their own people.ppl file inside their people/<workspace-name> folder.

  6. Inside that file, they will create their user by adding a user block that uses their ID from above. For example, Kevin Osei would type this in his people.ppl file:

    user kevin_osei {}
    
  7. This new user can now open this workspace in the People Work app by going to File > Open Workspace > Open Existing Workspace, and clicking on their newly created workspace folder.

Configuration

People Work is meant to be configuration-free while also providing easy out-of-the-box configuration offers that developers are accustomed to using.

There are two main configuration files:

  1. ~/.config/people/config.toml - configuration that is static and can be saved in a dotfiles repo.
  2. ~/.local/state/people/state.toml - configuration that is related to how the user is using the app and is machine-specific.

Application Configuration

This refers to global configuration for the user that can be saved in a dotfiles repo, does not change very often, is not sensitive, and is located in ~/.config/people/config.toml. The following properties are supported:

Default Workspaces Parent Directory

  • Value - default_workspaces_parent of type path.
  • Default - ~/Documents/People

The location of the parent folder that is used when a new workspace is created. The user might want to change this when they are using a synced folder location.

Example:

default_workspaces_parent = "~/Synced/Documents/People"

Workspaces

  • Value: workspaces of an array of paths
  • Default: [] (empty array)

The location workspaces that the user can switch between in the app.

Info

If any of the directories listed here no longer exist, they will be removed and the config file will be updated. This also applies to the current workspace in the state config.

Example:

workspaces = [
  "~/Docuemnts/People/My Corp",
  "~/Docuemnts/People/Local Tech Community"
]

State

This is only for reference; when you use the app it will update these values.

Current Workspace

  • Value: current_workspace that is a path
  • Default: none

The location workspaces that the user is currently working on. The app will automatically open to this location.

Example:

current_workspace = "~/Docuemnts/People/My Corp"