MY PROP JOURNAL

Playbooks

Read playbooks with strategies and entry/exit criteria.

List playbooks

Retrieve a paginated list of your trading playbooks, including associated strategies and entry/exit criteria.

Endpoint: GET /api/v1/playbooks

Query parameters

ParameterTypeDescription
searchstringSearch in name or description
strategy_idstringFilter by linked strategy UUID
tagsstringComma-separated tag IDs
formatstringContent format: json, html, or markdown
content_formatstringAlias for format
include_mediabooleanInclude extracted media URLs (default false)
offsetintegerPagination offset (default 0)
limitintegerPage size, max 100 (default 20)

Example requests

cURL:

curl "https://app.mypropjournal.com/api/v1/playbooks" \
  -H "Authorization: Bearer mpj_your_api_key_here" \
  -H "Content-Type: application/json"

JavaScript:

async function getPlaybooks(offset = 0, limit = 20) {
  const url = new URL('https://app.mypropjournal.com/api/v1/playbooks');
  url.searchParams.append('offset', offset);
  url.searchParams.append('limit', limit);
  
  const response = await fetch(url, {
    headers: {
      'Authorization': 'Bearer mpj_your_api_key_here',
      'Content-Type': 'application/json'
    }
  });
  
  return response.json();
}

const playbooks = await getPlaybooks();
console.log(`Total playbooks: ${playbooks.pagination.total}`);

playbooks.data.forEach(playbook => {
  console.log(`${playbook.name} - ${playbook.strategies.length} strategies`);
});

Python:

import requests

def get_playbooks(offset=0, limit=20):
    url = 'https://app.mypropjournal.com/api/v1/playbooks'
    headers = {
        'Authorization': 'Bearer mpj_your_api_key_here',
        'Content-Type': 'application/json'
    }
    params = {'offset': offset, 'limit': limit}
    
    response = requests.get(url, headers=headers, params=params)
    response.raise_for_status()
    return response.json()

playbooks = get_playbooks()

for playbook in playbooks['data']:
    print(f"{playbook['name']}")
    print(f"  Strategies: {len(playbook['strategies'])}")
    print(f"  Entry criteria: {len(playbook['entry_criteria'])}")
    print(f"  Exit criteria: {len(playbook['exit_criteria'])}")

Example response

{
  "data": [
    {
      "id": "a1b2c3d4-e5f6-7890-1234-567890abcdef",
      "name": "Momentum Trading Playbook",
      "description": "Strategies for momentum-based trades",
      "created_at": "2024-01-01T00:00:00Z",
      "updated_at": "2024-03-15T10:30:00Z",
      "entry_criteria": [
        {
          "id": "b2c3d4e5-f6g7-8901-2345-67890abcdef1",
          "description": "Price breaks above 20-day MA with volume",
          "order": 1
        },
        {
          "id": "c3d4e5f6-g7h8-9012-3456-7890abcdef12",
          "description": "RSI above 60",
          "order": 2
        }
      ],
      "exit_criteria": [
        {
          "id": "d4e5f6g7-h8i9-0123-4567-890abcdef123",
          "description": "Exit at 2:1 risk/reward or end of day",
          "order": 1
        },
        {
          "id": "e5f6g7h8-i9j0-1234-5678-90abcdef1234",
          "description": "Stop loss at 1% of account",
          "order": 2
        }
      ],
      "strategies": [
        {
          "id": "f6g7h8i9-j0k1-2345-6789-0abcdef12345",
          "name": "Gap and Go",
          "description": "Trade stocks gapping up on news",
          "created_at": "2024-01-01T00:00:00Z"
        },
        {
          "id": "g7h8i9j0-k1l2-3456-7890-abcdef123456",
          "name": "Opening Range Breakout",
          "description": "Break above first 15-minute range",
          "created_at": "2024-01-05T00:00:00Z"
        }
      ]
    }
  ],
  "pagination": {
    "total": 5,
    "limit": 20,
    "offset": 0,
    "has_more": false
  }
}

Response fields

Playbook object:

FieldTypeDescription
idstringUnique playbook identifier (UUID)
namestringPlaybook name
descriptionstringPlaybook description
created_atstringCreation timestamp (ISO 8601)
updated_atstringLast modification timestamp (ISO 8601)
entry_criteriaarrayArray of entry criterion objects
exit_criteriaarrayArray of exit criterion objects
strategiesarrayArray of strategy objects

Entry/Exit criterion object:

FieldTypeDescription
idstringUnique criterion identifier (UUID)
descriptionstringCriterion description
orderintegerDisplay order

Strategy object:

FieldTypeDescription
idstringUnique strategy identifier (UUID)
namestringStrategy name
descriptionstringStrategy description
created_atstringCreation timestamp (ISO 8601)

Get a single playbook

Retrieve detailed information for a specific playbook.

Endpoint: GET /api/v1/playbooks/{id}

Example request

cURL:

curl "https://app.mypropjournal.com/api/v1/playbooks/a1b2c3d4-e5f6-7890-1234-567890abcdef" \
  -H "Authorization: Bearer mpj_your_api_key_here" \
  -H "Content-Type: application/json"

JavaScript:

async function getPlaybook(playbookId) {
  const response = await fetch(
    `https://app.mypropjournal.com/api/v1/playbooks/${playbookId}`,
    {
      headers: {
        'Authorization': 'Bearer mpj_your_api_key_here',
        'Content-Type': 'application/json'
      }
    }
  );
  
  return response.json();
}

const playbook = await getPlaybook('a1b2c3d4-e5f6-7890-1234-567890abcdef');

console.log(`Playbook: ${playbook.data.name}`);
console.log('Entry Criteria:');
playbook.data.entry_criteria.forEach(criterion => {
  console.log(`  - ${criterion.description}`);
});

Python:

import requests

def get_playbook(playbook_id):
    url = f'https://app.mypropjournal.com/api/v1/playbooks/{playbook_id}'
    headers = {
        'Authorization': 'Bearer mpj_your_api_key_here',
        'Content-Type': 'application/json'
    }
    
    response = requests.get(url, headers=headers)
    response.raise_for_status()
    return response.json()

playbook = get_playbook('a1b2c3d4-e5f6-7890-1234-567890abcdef')

print(f"Playbook: {playbook['data']['name']}")
print(f"Description: {playbook['data']['description']}")
print(f"\nStrategies ({len(playbook['data']['strategies'])}):")
for strategy in playbook['data']['strategies']:
    print(f"  - {strategy['name']}: {strategy['description']}")

Example response

Returns a single playbook object with the same structure as shown in the list endpoint.

Create a playbook

Create a new playbook with strategies and rich content.

Endpoint: POST /api/v1/playbooks

Request body

FieldTypeRequiredDescription
titlestringYesPlaybook title
descriptionstringNoBrief description of the playbook
contentobjectNoTipTap JSON content
content_htmlstringNoHTML content (alternative to content)
content_markdownstringNoMarkdown content (alternative to content)
strategy_idsarrayNoArray of strategy UUIDs to link

Example request

curl -X POST "https://app.mypropjournal.com/api/v1/playbooks" \
  -H "Authorization: Bearer mpj_your_api_key_here" \
  -H "Content-Type: application/json" \
  -d '{
    "title": "Momentum Trading Playbook",
    "description": "High-probability momentum strategies",
    "content_markdown": "# Entry Criteria\n- Volume surge\n- Price above VWAP\n\n# Exit Rules\n- 2:1 RR target",
    "strategy_ids": ["abc-123", "def-456"]
  }'

Update a playbook

Update an existing playbook.

Endpoint: PUT /api/v1/playbooks/{id}

All fields are optional. Only provided fields will be updated.

Example request

curl -X PUT "https://app.mypropjournal.com/api/v1/playbooks/abc-123" \
  -H "Authorization: Bearer mpj_your_api_key_here" \
  -H "Content-Type: application/json" \
  -d '{
    "title": "Updated Playbook Title",
    "strategy_ids": ["abc-123", "def-456", "ghi-789"]
  }'

Delete a playbook

Delete a playbook permanently.

Endpoint: DELETE /api/v1/playbooks/{id}

Cascade Delete Warning

Deleting a playbook will permanently cascade delete the following related data:

  • All strategy associations linking strategies to this playbook

Additionally, these references will be set to null (not deleted):

  • Any trading plans linked to this playbook
  • Any chart books linked to this playbook

This action cannot be undone. The API response will include warnings about what data was affected.

Example request

curl -X DELETE "https://app.mypropjournal.com/api/v1/playbooks/abc-123" \
  -H "Authorization: Bearer mpj_your_api_key_here"

Common use cases

Export playbook checklist

async function exportPlaybookChecklist(playbookId) {
  const playbook = await getPlaybook(playbookId);
  const data = playbook.data;
  
  let checklist = `# ${data.name}\n\n`;
  checklist += `${data.description}\n\n`;
  
  checklist += `## Entry Criteria\n`;
  data.entry_criteria.forEach(criterion => {
    checklist += `- [ ] ${criterion.description}\n`;
  });
  
  checklist += `\n## Exit Criteria\n`;
  data.exit_criteria.forEach(criterion => {
    checklist += `- [ ] ${criterion.description}\n`;
  });
  
  return checklist;
}

const checklist = await exportPlaybookChecklist('playbook-id-here');
console.log(checklist);

Get all strategies across playbooks

def get_all_strategies():
    playbooks = get_playbooks(limit=100)
    all_strategies = []
    
    for playbook in playbooks['data']:
        for strategy in playbook['strategies']:
            strategy['playbook_name'] = playbook['name']
            all_strategies.append(strategy)
    
    return all_strategies

strategies = get_all_strategies()
print(f"Total strategies across all playbooks: {len(strategies)}")

for strategy in strategies:
    print(f"{strategy['name']} (from {strategy['playbook_name']})")

Find playbooks by strategy name

async function findPlaybooksByStrategy(strategyName) {
  const playbooks = await getPlaybooks();
  
  return playbooks.data.filter(playbook => 
    playbook.strategies.some(strategy => 
      strategy.name.toLowerCase().includes(strategyName.toLowerCase())
    )
  );
}

const momentumPlaybooks = await findPlaybooksByStrategy('momentum');
console.log(`Found ${momentumPlaybooks.length} playbooks with momentum strategies`);

Error responses

401 Unauthorized

Missing or invalid API key:

{
  "error": "Invalid API key",
  "code": "INVALID_API_KEY"
}

404 Not Found

Playbook doesn't exist or doesn't belong to you:

{
  "error": "Playbook not found",
  "code": "NOT_FOUND"
}