@commandable/integration-data 0.0.5 → 0.0.7
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/credentials-index.d.ts.map +1 -1
- package/dist/credentials-index.js +183 -0
- package/dist/credentials-index.js.map +1 -1
- package/dist/index.d.ts +2 -2
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +1 -1
- package/dist/index.js.map +1 -1
- package/dist/loader.d.ts +33 -0
- package/dist/loader.d.ts.map +1 -1
- package/dist/loader.js +36 -4
- package/dist/loader.js.map +1 -1
- package/integrations/__tests__/liveHarness.ts +16 -3
- package/integrations/airtable/.env.test +9 -0
- package/integrations/airtable/.env.test.example +11 -0
- package/integrations/airtable/README.md +27 -0
- package/integrations/airtable/__tests__/get_handlers.test.ts +43 -5
- package/integrations/confluence/.env.test +25 -0
- package/integrations/confluence/.env.test.example +36 -0
- package/integrations/confluence/README.md +28 -0
- package/integrations/confluence/__tests__/get_handlers.test.ts +121 -0
- package/integrations/confluence/__tests__/usage_parity.test.ts +14 -0
- package/integrations/confluence/__tests__/write_handlers.test.ts +131 -0
- package/integrations/confluence/credentials.json +39 -0
- package/integrations/confluence/credentials_hint.md +4 -0
- package/integrations/confluence/credentials_hint_api_token.md +9 -0
- package/integrations/confluence/credentials_hint_oauth_token.md +8 -0
- package/integrations/confluence/handlers/add_comment.js +19 -0
- package/integrations/confluence/handlers/add_label.js +16 -0
- package/integrations/confluence/handlers/create_page.js +22 -0
- package/integrations/confluence/handlers/delete_page.js +17 -0
- package/integrations/confluence/handlers/get_comments.js +33 -0
- package/integrations/confluence/handlers/get_page_children.js +30 -0
- package/integrations/confluence/handlers/get_space.js +22 -0
- package/integrations/confluence/handlers/list_spaces.js +39 -0
- package/integrations/confluence/handlers/read_page.js +49 -0
- package/integrations/confluence/handlers/search_pages.js +42 -0
- package/integrations/confluence/handlers/update_page.js +42 -0
- package/integrations/confluence/manifest.json +85 -0
- package/integrations/confluence/prompt.md +55 -0
- package/integrations/confluence/schemas/add_comment.json +22 -0
- package/integrations/confluence/schemas/add_label.json +19 -0
- package/integrations/confluence/schemas/create_page.json +33 -0
- package/integrations/confluence/schemas/delete_page.json +23 -0
- package/integrations/confluence/schemas/empty.json +6 -0
- package/integrations/confluence/schemas/get_comments.json +24 -0
- package/integrations/confluence/schemas/get_page_children.json +28 -0
- package/integrations/confluence/schemas/get_space.json +18 -0
- package/integrations/confluence/schemas/list_spaces.json +36 -0
- package/integrations/confluence/schemas/read_page.json +28 -0
- package/integrations/confluence/schemas/search_pages.json +26 -0
- package/integrations/confluence/schemas/update_page.json +31 -0
- package/integrations/github/.env.test +16 -0
- package/integrations/github/.env.test.example +17 -0
- package/integrations/github/README.md +75 -0
- package/integrations/github/__tests__/get_handlers.test.ts +207 -12
- package/integrations/github/__tests__/write_handlers.test.ts +323 -55
- package/integrations/github/handlers/create_commit.js +10 -2
- package/integrations/github/handlers/create_file.js +46 -0
- package/integrations/github/handlers/create_pull_request_review.js +10 -0
- package/integrations/github/handlers/create_release.js +14 -0
- package/integrations/github/handlers/delete_branch.js +8 -0
- package/integrations/github/handlers/delete_file.js +22 -0
- package/integrations/github/handlers/edit_file.js +52 -0
- package/integrations/github/handlers/edit_files.js +107 -0
- package/integrations/github/handlers/fork_repo.js +10 -0
- package/integrations/github/handlers/get_commit.js +8 -0
- package/integrations/github/handlers/get_file_contents.js +21 -0
- package/integrations/github/handlers/get_job_logs.js +6 -0
- package/integrations/github/handlers/get_latest_release.js +4 -0
- package/integrations/github/handlers/get_me.js +4 -0
- package/integrations/github/handlers/get_pull_request.js +4 -0
- package/integrations/github/handlers/get_pull_request_diff.js +8 -0
- package/integrations/github/handlers/get_repo_tree.js +12 -0
- package/integrations/github/handlers/get_workflow_run.js +4 -0
- package/integrations/github/handlers/list_branches.js +6 -1
- package/integrations/github/handlers/list_commits.js +5 -6
- package/integrations/github/handlers/list_issue_comments.js +8 -0
- package/integrations/github/handlers/list_issues.js +5 -6
- package/integrations/github/handlers/list_labels.js +8 -0
- package/integrations/github/handlers/list_pull_request_comments.js +8 -0
- package/integrations/github/handlers/list_pull_request_files.js +8 -0
- package/integrations/github/handlers/list_pull_requests.js +7 -2
- package/integrations/github/handlers/list_releases.js +8 -0
- package/integrations/github/handlers/list_tags.js +8 -0
- package/integrations/github/handlers/list_workflow_runs.js +11 -0
- package/integrations/github/handlers/request_pull_request_reviewers.js +10 -0
- package/integrations/github/handlers/search_code.js +8 -0
- package/integrations/github/handlers/search_issues.js +8 -0
- package/integrations/github/handlers/search_pull_requests.js +8 -0
- package/integrations/github/handlers/search_repos.js +10 -0
- package/integrations/github/handlers/update_pull_request.js +13 -0
- package/integrations/github/manifest.json +86 -21
- package/integrations/github/prompt.md +36 -0
- package/integrations/github/schemas/create_file.json +13 -0
- package/integrations/github/schemas/create_pull_request_review.json +17 -0
- package/integrations/github/schemas/create_release.json +16 -0
- package/integrations/github/schemas/delete_branch.json +10 -0
- package/integrations/github/schemas/delete_file.json +13 -0
- package/integrations/github/schemas/edit_file.json +26 -0
- package/integrations/github/schemas/edit_files.json +39 -0
- package/integrations/github/schemas/fork_repo.json +11 -0
- package/integrations/github/schemas/get_commit.json +12 -0
- package/integrations/github/schemas/get_file_contents.json +11 -0
- package/integrations/github/schemas/get_job_logs.json +10 -0
- package/integrations/github/schemas/get_pull_request.json +10 -0
- package/integrations/github/schemas/get_pull_request_diff.json +10 -0
- package/integrations/github/schemas/get_repo_tree.json +12 -0
- package/integrations/github/schemas/get_workflow_run.json +10 -0
- package/integrations/github/schemas/list_branches.json +12 -0
- package/integrations/github/schemas/list_commits.json +5 -3
- package/integrations/github/schemas/list_issue_comments.json +12 -0
- package/integrations/github/schemas/list_issues.json +4 -2
- package/integrations/github/schemas/list_labels.json +11 -0
- package/integrations/github/schemas/list_pull_request_comments.json +12 -0
- package/integrations/github/schemas/list_pull_request_files.json +12 -0
- package/integrations/github/schemas/list_pull_requests.json +7 -1
- package/integrations/github/schemas/list_releases.json +11 -0
- package/integrations/github/schemas/list_tags.json +11 -0
- package/integrations/github/schemas/list_workflow_runs.json +18 -0
- package/integrations/github/schemas/request_pull_request_reviewers.json +20 -0
- package/integrations/github/schemas/search_code.json +10 -0
- package/integrations/github/schemas/search_issues.json +10 -0
- package/integrations/github/schemas/search_pull_requests.json +10 -0
- package/integrations/github/schemas/search_repos.json +12 -0
- package/integrations/github/schemas/update_pull_request.json +15 -0
- package/integrations/google-calendar/.env.test.example +11 -0
- package/integrations/google-calendar/README.md +41 -0
- package/integrations/google-calendar/__tests__/write_and_admin_handlers.test.ts +7 -20
- package/integrations/google-calendar/handlers/get_event.js +5 -1
- package/integrations/google-calendar/handlers/list_events.js +2 -0
- package/integrations/google-calendar/manifest.json +27 -18
- package/integrations/google-calendar/prompt.md +68 -0
- package/integrations/google-calendar/schemas/id_calendar_event.json +4 -2
- package/integrations/google-calendar/schemas/list_events.json +10 -8
- package/integrations/google-docs/README.md +30 -0
- package/integrations/google-docs/__tests__/get_handlers.test.ts +4 -19
- package/integrations/google-docs/__tests__/write_handlers.test.ts +31 -48
- package/integrations/google-docs/handlers/read_document.js +189 -0
- package/integrations/google-docs/manifest.json +16 -31
- package/integrations/google-docs/prompt.md +49 -0
- package/integrations/google-docs/schemas/{get_document_text.json → read_document.json} +5 -2
- package/integrations/google-docs/todo.md +18 -0
- package/integrations/google-drive/README.md +26 -0
- package/integrations/google-drive/__tests__/handlers.test.ts +43 -0
- package/integrations/google-drive/__tests__/usage_parity.test.ts +9 -0
- package/integrations/google-drive/handlers/get_file.js +2 -4
- package/integrations/google-drive/handlers/get_file_content.js +41 -0
- package/integrations/google-drive/handlers/list_files.js +15 -0
- package/integrations/google-drive/handlers/search_files.js +20 -0
- package/integrations/google-drive/handlers/share_file.js +20 -0
- package/integrations/google-drive/manifest.json +37 -10
- package/integrations/google-drive/prompt.md +59 -0
- package/integrations/google-drive/schemas/get_file.json +2 -2
- package/integrations/google-drive/schemas/get_file_content.json +11 -0
- package/integrations/google-drive/schemas/list_files.json +12 -0
- package/integrations/google-drive/schemas/search_files.json +14 -0
- package/integrations/google-drive/schemas/share_file.json +23 -0
- package/integrations/google-gmail/.env.test.example +11 -0
- package/integrations/google-gmail/README.md +49 -0
- package/integrations/google-gmail/__tests__/get_handlers.test.ts +134 -0
- package/integrations/google-gmail/__tests__/usage_parity.test.ts +9 -0
- package/integrations/google-gmail/__tests__/write_and_admin_handlers.test.ts +211 -0
- package/integrations/google-gmail/credentials.json +57 -0
- package/integrations/google-gmail/credentials_hint_oauth_token.md +8 -0
- package/integrations/google-gmail/credentials_hint_service_account.md +10 -0
- package/integrations/google-gmail/handlers/create_draft_email.js +27 -0
- package/integrations/google-gmail/handlers/create_label.js +12 -0
- package/integrations/google-gmail/handlers/delete_draft.js +13 -0
- package/integrations/google-gmail/handlers/delete_label.js +13 -0
- package/integrations/google-gmail/handlers/delete_message.js +13 -0
- package/integrations/google-gmail/handlers/delete_thread.js +13 -0
- package/integrations/google-gmail/handlers/get_draft.js +6 -0
- package/integrations/google-gmail/handlers/get_label.js +6 -0
- package/integrations/google-gmail/handlers/get_message.js +14 -0
- package/integrations/google-gmail/handlers/get_profile.js +5 -0
- package/integrations/google-gmail/handlers/get_thread.js +14 -0
- package/integrations/google-gmail/handlers/list_drafts.js +15 -0
- package/integrations/google-gmail/handlers/list_labels.js +5 -0
- package/integrations/google-gmail/handlers/list_messages.js +19 -0
- package/integrations/google-gmail/handlers/list_threads.js +19 -0
- package/integrations/google-gmail/handlers/modify_message.js +11 -0
- package/integrations/google-gmail/handlers/modify_thread.js +11 -0
- package/integrations/google-gmail/handlers/read_email.js +56 -0
- package/integrations/google-gmail/handlers/send_draft.js +15 -0
- package/integrations/google-gmail/handlers/send_email.js +22 -0
- package/integrations/google-gmail/handlers/trash_message.js +6 -0
- package/integrations/google-gmail/handlers/trash_thread.js +6 -0
- package/integrations/google-gmail/handlers/untrash_message.js +6 -0
- package/integrations/google-gmail/handlers/untrash_thread.js +6 -0
- package/integrations/google-gmail/handlers/update_label.js +15 -0
- package/integrations/google-gmail/manifest.json +44 -0
- package/integrations/google-gmail/prompt.md +52 -0
- package/integrations/google-gmail/schemas/create_draft_email.json +16 -0
- package/integrations/google-gmail/schemas/create_label.json +26 -0
- package/integrations/google-gmail/schemas/get_message.json +20 -0
- package/integrations/{google-docs/schemas/get_document_structured.json → google-gmail/schemas/get_profile.json} +4 -2
- package/integrations/google-gmail/schemas/get_thread.json +20 -0
- package/integrations/google-gmail/schemas/id_draft.json +16 -0
- package/integrations/google-gmail/schemas/id_label.json +16 -0
- package/integrations/google-gmail/schemas/id_message.json +16 -0
- package/integrations/google-gmail/schemas/id_thread.json +16 -0
- package/integrations/google-gmail/schemas/list_drafts.json +30 -0
- package/integrations/{google-sheet/schemas/get_developer_metadata.json → google-gmail/schemas/list_labels.json} +4 -3
- package/integrations/google-gmail/schemas/list_messages.json +35 -0
- package/integrations/google-gmail/schemas/list_threads.json +35 -0
- package/integrations/google-gmail/schemas/modify_message.json +24 -0
- package/integrations/google-gmail/schemas/modify_thread.json +24 -0
- package/integrations/google-gmail/schemas/read_email.json +10 -0
- package/integrations/google-gmail/schemas/send_draft.json +29 -0
- package/integrations/google-gmail/schemas/send_email.json +17 -0
- package/integrations/google-gmail/schemas/update_label.json +33 -0
- package/integrations/google-sheet/README.md +27 -0
- package/integrations/google-sheet/__tests__/get_handlers.test.ts +6 -52
- package/integrations/google-sheet/__tests__/write_handlers.test.ts +0 -20
- package/integrations/google-sheet/handlers/get_spreadsheet.js +2 -0
- package/integrations/google-sheet/handlers/read_sheet.js +75 -0
- package/integrations/google-sheet/manifest.json +13 -62
- package/integrations/google-sheet/prompt.md +49 -0
- package/integrations/google-sheet/schemas/get_spreadsheet.json +5 -4
- package/integrations/google-sheet/schemas/read_sheet.json +21 -0
- package/integrations/google-slides/README.md +28 -0
- package/integrations/google-slides/__tests__/get_handlers.test.ts +12 -9
- package/integrations/google-slides/handlers/read_presentation.js +51 -0
- package/integrations/google-slides/manifest.json +13 -13
- package/integrations/google-slides/prompt.md +56 -0
- package/integrations/hubspot/.env.test.example +20 -0
- package/integrations/hubspot/README.md +48 -0
- package/integrations/hubspot/__tests__/get_handlers.test.ts +151 -0
- package/integrations/hubspot/__tests__/usage_parity.test.ts +10 -0
- package/integrations/hubspot/__tests__/write_handlers.test.ts +244 -0
- package/integrations/hubspot/credentials.json +48 -0
- package/integrations/hubspot/credentials_hint.md +20 -0
- package/integrations/hubspot/credentials_hint_oauth_token.md +16 -0
- package/integrations/hubspot/handlers/archive_company.js +13 -0
- package/integrations/hubspot/handlers/archive_contact.js +13 -0
- package/integrations/hubspot/handlers/archive_deal.js +13 -0
- package/integrations/hubspot/handlers/archive_ticket.js +13 -0
- package/integrations/hubspot/handlers/create_association.js +18 -0
- package/integrations/hubspot/handlers/create_company.js +13 -0
- package/integrations/hubspot/handlers/create_contact.js +14 -0
- package/integrations/hubspot/handlers/create_deal.js +16 -0
- package/integrations/hubspot/handlers/create_note.js +44 -0
- package/integrations/hubspot/handlers/create_task.js +48 -0
- package/integrations/hubspot/handlers/create_ticket.js +15 -0
- package/integrations/hubspot/handlers/get_associations.js +14 -0
- package/integrations/hubspot/handlers/get_company.js +18 -0
- package/integrations/hubspot/handlers/get_contact.js +18 -0
- package/integrations/hubspot/handlers/get_deal.js +18 -0
- package/integrations/hubspot/handlers/get_ticket.js +20 -0
- package/integrations/hubspot/handlers/list_owners.js +12 -0
- package/integrations/hubspot/handlers/list_pipelines.js +5 -0
- package/integrations/hubspot/handlers/list_properties.js +11 -0
- package/integrations/hubspot/handlers/remove_association.js +22 -0
- package/integrations/hubspot/handlers/search_companies.js +43 -0
- package/integrations/hubspot/handlers/search_contacts.js +43 -0
- package/integrations/hubspot/handlers/search_deals.js +43 -0
- package/integrations/hubspot/handlers/search_notes.js +43 -0
- package/integrations/hubspot/handlers/search_tasks.js +43 -0
- package/integrations/hubspot/handlers/search_tickets.js +43 -0
- package/integrations/hubspot/handlers/update_company.js +13 -0
- package/integrations/hubspot/handlers/update_contact.js +14 -0
- package/integrations/hubspot/handlers/update_deal.js +16 -0
- package/integrations/hubspot/handlers/update_task.js +17 -0
- package/integrations/hubspot/handlers/update_ticket.js +15 -0
- package/integrations/hubspot/manifest.json +230 -0
- package/integrations/hubspot/prompt.md +69 -0
- package/integrations/hubspot/schemas/archive_company.json +13 -0
- package/integrations/hubspot/schemas/archive_contact.json +13 -0
- package/integrations/hubspot/schemas/archive_deal.json +9 -0
- package/integrations/hubspot/schemas/archive_ticket.json +9 -0
- package/integrations/hubspot/schemas/create_association.json +24 -0
- package/integrations/hubspot/schemas/create_company.json +14 -0
- package/integrations/hubspot/schemas/create_contact.json +15 -0
- package/integrations/hubspot/schemas/create_deal.json +20 -0
- package/integrations/hubspot/schemas/create_note.json +37 -0
- package/integrations/hubspot/schemas/create_task.json +51 -0
- package/integrations/hubspot/schemas/create_ticket.json +16 -0
- package/integrations/hubspot/schemas/empty.json +6 -0
- package/integrations/hubspot/schemas/get_associations.json +30 -0
- package/integrations/hubspot/schemas/get_company.json +27 -0
- package/integrations/hubspot/schemas/get_contact.json +27 -0
- package/integrations/hubspot/schemas/get_deal.json +20 -0
- package/integrations/hubspot/schemas/get_ticket.json +20 -0
- package/integrations/hubspot/schemas/list_owners.json +25 -0
- package/integrations/hubspot/schemas/list_pipelines.json +13 -0
- package/integrations/hubspot/schemas/list_properties.json +17 -0
- package/integrations/hubspot/schemas/remove_association.json +24 -0
- package/integrations/hubspot/schemas/search_companies.json +56 -0
- package/integrations/hubspot/schemas/search_contacts.json +56 -0
- package/integrations/hubspot/schemas/search_deals.json +43 -0
- package/integrations/hubspot/schemas/search_notes.json +43 -0
- package/integrations/hubspot/schemas/search_tasks.json +43 -0
- package/integrations/hubspot/schemas/search_tickets.json +43 -0
- package/integrations/hubspot/schemas/update_company.json +20 -0
- package/integrations/hubspot/schemas/update_contact.json +21 -0
- package/integrations/hubspot/schemas/update_deal.json +19 -0
- package/integrations/hubspot/schemas/update_task.json +31 -0
- package/integrations/hubspot/schemas/update_ticket.json +18 -0
- package/integrations/jira/.env.test +46 -0
- package/integrations/jira/.env.test.example +41 -0
- package/integrations/jira/README.md +46 -0
- package/integrations/jira/__tests__/get_handlers.test.ts +193 -0
- package/integrations/jira/__tests__/usage_parity.test.ts +14 -0
- package/integrations/jira/__tests__/write_handlers.test.ts +157 -0
- package/integrations/jira/credentials.json +39 -0
- package/integrations/jira/credentials_hint.md +4 -0
- package/integrations/jira/credentials_hint_api_token.md +6 -0
- package/integrations/jira/credentials_hint_oauth_token.md +6 -0
- package/integrations/jira/handlers/add_comment.js +9 -0
- package/integrations/jira/handlers/assign_issue.js +11 -0
- package/integrations/jira/handlers/create_issue.js +37 -0
- package/integrations/jira/handlers/create_sprint.js +19 -0
- package/integrations/jira/handlers/delete_issue.js +10 -0
- package/integrations/jira/handlers/get_backlog_issues.js +13 -0
- package/integrations/jira/handlers/get_board.js +6 -0
- package/integrations/jira/handlers/get_issue.js +63 -0
- package/integrations/jira/handlers/get_issue_comments.js +31 -0
- package/integrations/jira/handlers/get_myself.js +14 -0
- package/integrations/jira/handlers/get_project.js +28 -0
- package/integrations/jira/handlers/get_sprint.js +5 -0
- package/integrations/jira/handlers/get_sprint_issues.js +13 -0
- package/integrations/jira/handlers/get_transitions.js +23 -0
- package/integrations/jira/handlers/list_boards.js +34 -0
- package/integrations/jira/handlers/list_projects.js +29 -0
- package/integrations/jira/handlers/list_sprints.js +29 -0
- package/integrations/jira/handlers/move_issues_to_sprint.js +11 -0
- package/integrations/jira/handlers/search_issues.js +43 -0
- package/integrations/jira/handlers/search_users.js +21 -0
- package/integrations/jira/handlers/transition_issue.js +44 -0
- package/integrations/jira/handlers/update_issue.js +40 -0
- package/integrations/jira/handlers/update_sprint.js +20 -0
- package/integrations/jira/manifest.json +204 -0
- package/integrations/jira/prompt.md +80 -0
- package/integrations/jira/schemas/add_comment.json +16 -0
- package/integrations/jira/schemas/assign_issue.json +16 -0
- package/integrations/jira/schemas/create_issue.json +49 -0
- package/integrations/jira/schemas/create_sprint.json +29 -0
- package/integrations/jira/schemas/delete_issue.json +12 -0
- package/integrations/jira/schemas/empty.json +6 -0
- package/integrations/jira/schemas/get_backlog_issues.json +33 -0
- package/integrations/jira/schemas/get_board.json +13 -0
- package/integrations/jira/schemas/get_issue.json +23 -0
- package/integrations/jira/schemas/get_issue_comments.json +23 -0
- package/integrations/jira/schemas/get_project.json +17 -0
- package/integrations/jira/schemas/get_sprint.json +13 -0
- package/integrations/jira/schemas/get_sprint_issues.json +33 -0
- package/integrations/jira/schemas/get_transitions.json +12 -0
- package/integrations/jira/schemas/list_boards.json +27 -0
- package/integrations/jira/schemas/list_projects.json +22 -0
- package/integrations/jira/schemas/list_sprints.json +29 -0
- package/integrations/jira/schemas/move_issues_to_sprint.json +19 -0
- package/integrations/jira/schemas/search_issues.json +28 -0
- package/integrations/jira/schemas/search_users.json +18 -0
- package/integrations/jira/schemas/transition_issue.json +38 -0
- package/integrations/jira/schemas/update_issue.json +47 -0
- package/integrations/jira/schemas/update_sprint.json +33 -0
- package/integrations/new_integration_prompt.md +177 -2
- package/integrations/notion/.env.test +10 -0
- package/integrations/notion/.env.test.example +13 -0
- package/integrations/notion/README.md +42 -0
- package/integrations/notion/manifest.json +64 -35
- package/integrations/trello/.env.test +6 -0
- package/integrations/trello/.env.test.example +9 -0
- package/integrations/trello/README.md +50 -0
- package/package.json +7 -3
- package/integrations/google-calendar/handlers/update_event.js +0 -5
- package/integrations/google-calendar/schemas/update_event.json +0 -10
- package/integrations/google-docs/handlers/get_document.js +0 -12
- package/integrations/google-docs/handlers/get_document_structured.js +0 -6
- package/integrations/google-docs/handlers/get_document_text.js +0 -17
- package/integrations/google-docs/schemas/get_document.json +0 -11
- package/integrations/google-sheet/handlers/batch_clear_values_by_data_filter.js +0 -6
- package/integrations/google-sheet/handlers/batch_get_values.js +0 -16
- package/integrations/google-sheet/handlers/batch_update_values_by_data_filter.js +0 -16
- package/integrations/google-sheet/handlers/get_developer_metadata.js +0 -6
- package/integrations/google-sheet/handlers/get_spreadsheet_by_data_filter.js +0 -10
- package/integrations/google-sheet/handlers/get_values.js +0 -14
- package/integrations/google-sheet/handlers/get_values_by_data_filter.js +0 -14
- package/integrations/google-sheet/handlers/search_developer_metadata.js +0 -7
- package/integrations/google-sheet/schemas/batch_clear_values_by_data_filter.json +0 -10
- package/integrations/google-sheet/schemas/batch_get_values.json +0 -13
- package/integrations/google-sheet/schemas/batch_update_values_by_data_filter.json +0 -25
- package/integrations/google-sheet/schemas/get_spreadsheet_by_data_filter.json +0 -11
- package/integrations/google-sheet/schemas/get_values.json +0 -13
- package/integrations/google-sheet/schemas/get_values_by_data_filter.json +0 -17
- package/integrations/google-sheet/schemas/search_developer_metadata.json +0 -14
- package/integrations/google-slides/handlers/get_presentation.js +0 -6
|
@@ -3,11 +3,11 @@ import { createCredentialStore, createIntegrationNode, createProxy, createToolbo
|
|
|
3
3
|
|
|
4
4
|
// LIVE GitHub write tests -- runs once per available credential variant.
|
|
5
5
|
// Required env vars (at least one):
|
|
6
|
-
// -
|
|
7
|
-
// -
|
|
6
|
+
// - _GITHUB_CLASSIC_PAT (tests all write tools including create_repo/delete_repo)
|
|
7
|
+
// - _GITHUB_FINE_GRAINED_PAT (tests write tools; create_repo/delete_repo are excluded for this variant)
|
|
8
8
|
// Plus:
|
|
9
|
-
// -
|
|
10
|
-
// -
|
|
9
|
+
// - _GITHUB_TEST_OWNER
|
|
10
|
+
// - _GITHUB_TEST_REPO
|
|
11
11
|
|
|
12
12
|
const env = process.env as Record<string, string | undefined>
|
|
13
13
|
|
|
@@ -17,19 +17,40 @@ interface VariantConfig {
|
|
|
17
17
|
}
|
|
18
18
|
|
|
19
19
|
const variants: VariantConfig[] = [
|
|
20
|
-
{ key: 'classic_pat', token: env.
|
|
21
|
-
{ key: 'fine_grained_pat', token: env.
|
|
20
|
+
{ key: 'classic_pat', token: env._GITHUB_CLASSIC_PAT || '' },
|
|
21
|
+
{ key: 'fine_grained_pat', token: env._GITHUB_FINE_GRAINED_PAT || '' },
|
|
22
22
|
].filter(v => v.token.trim().length > 0)
|
|
23
23
|
|
|
24
|
-
const hasWriteEnv = hasEnv('
|
|
24
|
+
const hasWriteEnv = hasEnv('_GITHUB_TEST_OWNER', '_GITHUB_TEST_REPO')
|
|
25
25
|
const suiteOrSkip = (variants.length > 0 && hasWriteEnv) ? describe : describe.skip
|
|
26
26
|
|
|
27
|
+
async function withRetry<T>(
|
|
28
|
+
fn: () => Promise<T>,
|
|
29
|
+
{ maxAttempts = 3, delayMs = 2000, retryIf = (_e: unknown): boolean => true } = {},
|
|
30
|
+
): Promise<T> {
|
|
31
|
+
let lastError: unknown
|
|
32
|
+
for (let attempt = 1; attempt <= maxAttempts; attempt++) {
|
|
33
|
+
try {
|
|
34
|
+
return await fn()
|
|
35
|
+
}
|
|
36
|
+
catch (error) {
|
|
37
|
+
lastError = error
|
|
38
|
+
if (attempt < maxAttempts && retryIf(error)) {
|
|
39
|
+
await new Promise(resolve => setTimeout(resolve, delayMs * attempt))
|
|
40
|
+
continue
|
|
41
|
+
}
|
|
42
|
+
break
|
|
43
|
+
}
|
|
44
|
+
}
|
|
45
|
+
throw lastError
|
|
46
|
+
}
|
|
47
|
+
|
|
27
48
|
suiteOrSkip('github write handlers (live)', () => {
|
|
28
49
|
for (const variant of variants) {
|
|
29
50
|
describe(`variant: ${variant.key}`, () => {
|
|
30
51
|
const ctx = {
|
|
31
|
-
owner: env.
|
|
32
|
-
repo: env.
|
|
52
|
+
owner: env._GITHUB_TEST_OWNER,
|
|
53
|
+
repo: env._GITHUB_TEST_REPO,
|
|
33
54
|
}
|
|
34
55
|
let toolbox: ReturnType<typeof createToolbox>
|
|
35
56
|
|
|
@@ -40,7 +61,7 @@ suiteOrSkip('github write handlers (live)', () => {
|
|
|
40
61
|
toolbox = createToolbox('github', proxy, node, variant.key)
|
|
41
62
|
}, 30000)
|
|
42
63
|
|
|
43
|
-
it('create_issue -> update_issue -> comment_on_issue -> close_issue roundtrip', async () => {
|
|
64
|
+
it('create_issue -> update_issue -> comment_on_issue -> list_issue_comments -> close_issue roundtrip', async () => {
|
|
44
65
|
if (!ctx.owner || !ctx.repo)
|
|
45
66
|
return expect(true).toBe(true)
|
|
46
67
|
|
|
@@ -59,11 +80,56 @@ suiteOrSkip('github write handlers (live)', () => {
|
|
|
59
80
|
const comment = await comment_on_issue({ owner: ctx.owner, repo: ctx.repo, issue_number, body: 'A comment from test.' })
|
|
60
81
|
expect(comment?.id).toBeTruthy()
|
|
61
82
|
|
|
83
|
+
const list_issue_comments = toolbox.read('list_issue_comments')
|
|
84
|
+
const comments = await list_issue_comments({ owner: ctx.owner, repo: ctx.repo, issue_number })
|
|
85
|
+
expect(Array.isArray(comments)).toBe(true)
|
|
86
|
+
expect(comments.length).toBeGreaterThan(0)
|
|
87
|
+
|
|
62
88
|
const close_issue = toolbox.write('close_issue')
|
|
63
89
|
const closed = await close_issue({ owner: ctx.owner, repo: ctx.repo, issue_number })
|
|
64
90
|
expect(closed?.state).toBe('closed')
|
|
65
91
|
}, 90000)
|
|
66
92
|
|
|
93
|
+
it('fork_repo forks a public repo (best effort)', async () => {
|
|
94
|
+
if (!ctx.owner || !ctx.repo)
|
|
95
|
+
return expect(true).toBe(true)
|
|
96
|
+
const fork_repo = toolbox.write('fork_repo')
|
|
97
|
+
try {
|
|
98
|
+
const result = await fork_repo({ owner: ctx.owner, repo: ctx.repo })
|
|
99
|
+
// Fork returns the forked repo details
|
|
100
|
+
expect(result).toBeTruthy()
|
|
101
|
+
}
|
|
102
|
+
catch {
|
|
103
|
+
// May fail if repo is private or fork already exists -- that's ok
|
|
104
|
+
expect(true).toBe(true)
|
|
105
|
+
}
|
|
106
|
+
}, 30000)
|
|
107
|
+
|
|
108
|
+
it('create_release creates a draft release (classic_pat only)', async () => {
|
|
109
|
+
if (!toolbox.hasTool('write', 'create_repo'))
|
|
110
|
+
return expect(true).toBe(true)
|
|
111
|
+
if (!ctx.owner || !ctx.repo)
|
|
112
|
+
return expect(true).toBe(true)
|
|
113
|
+
const create_release = toolbox.write('create_release')
|
|
114
|
+
const tagName = `v0.0.0-test-${Date.now()}`
|
|
115
|
+
try {
|
|
116
|
+
const result = await create_release({
|
|
117
|
+
owner: ctx.owner,
|
|
118
|
+
repo: ctx.repo,
|
|
119
|
+
tag_name: tagName,
|
|
120
|
+
name: `Test Release ${tagName}`,
|
|
121
|
+
body: 'Draft release created by integration tests.',
|
|
122
|
+
draft: true,
|
|
123
|
+
})
|
|
124
|
+
expect(result?.tag_name).toBe(tagName)
|
|
125
|
+
expect(result?.draft).toBe(true)
|
|
126
|
+
}
|
|
127
|
+
catch {
|
|
128
|
+
// May fail if insufficient permissions -- that's ok
|
|
129
|
+
expect(true).toBe(true)
|
|
130
|
+
}
|
|
131
|
+
}, 30000)
|
|
132
|
+
|
|
67
133
|
it('create_repo -> delete_repo lifecycle (classic_pat only)', async () => {
|
|
68
134
|
if (!toolbox.hasTool('write', 'create_repo')) {
|
|
69
135
|
return expect(true).toBe(true)
|
|
@@ -80,12 +146,10 @@ suiteOrSkip('github write handlers (live)', () => {
|
|
|
80
146
|
})
|
|
81
147
|
expect(created?.name).toBe(repoName)
|
|
82
148
|
|
|
83
|
-
// /user/repos creates under the authenticated user, not necessarily ctx.owner
|
|
84
149
|
const createdOwner = created?.owner?.login
|
|
85
150
|
expect(createdOwner).toBeTruthy()
|
|
86
151
|
expect(created?.full_name).toBe(`${createdOwner}/${repoName}`)
|
|
87
152
|
|
|
88
|
-
// GitHub needs a moment to finish provisioning the repo before it can be deleted
|
|
89
153
|
await new Promise(resolve => setTimeout(resolve, 3000))
|
|
90
154
|
|
|
91
155
|
const delete_repo = toolbox.write('delete_repo')
|
|
@@ -94,84 +158,233 @@ suiteOrSkip('github write handlers (live)', () => {
|
|
|
94
158
|
expect(deleted?.status).toBe(204)
|
|
95
159
|
}, 90000)
|
|
96
160
|
|
|
97
|
-
it('
|
|
161
|
+
it('create_file: create, overwrite, and verify', async () => {
|
|
98
162
|
if (!ctx.owner || !ctx.repo)
|
|
99
163
|
return expect(true).toBe(true)
|
|
100
164
|
|
|
101
165
|
const timestamp = Date.now()
|
|
102
|
-
const branchName = `test-
|
|
166
|
+
const branchName = `test-create-file-${timestamp}`
|
|
167
|
+
const filePath = `test-create-${timestamp}.txt`
|
|
103
168
|
|
|
104
169
|
const create_branch = toolbox.write('create_branch')
|
|
105
170
|
const branch = await create_branch({ owner: ctx.owner, repo: ctx.repo, branch: branchName })
|
|
106
171
|
expect(branch?.ref).toBe(`refs/heads/${branchName}`)
|
|
107
172
|
|
|
108
|
-
const
|
|
109
|
-
const
|
|
173
|
+
const create_file = toolbox.write('create_file')
|
|
174
|
+
const created = await create_file({
|
|
110
175
|
owner: ctx.owner,
|
|
111
176
|
repo: ctx.repo,
|
|
112
|
-
|
|
113
|
-
|
|
177
|
+
branch: branchName,
|
|
178
|
+
path: filePath,
|
|
114
179
|
content: `Test content with UTF-8: Hello 世界 🌍\nCreated at ${timestamp}`,
|
|
180
|
+
message: `Add test file ${timestamp}`,
|
|
181
|
+
})
|
|
182
|
+
expect(created?.commit?.sha).toBeTruthy()
|
|
183
|
+
expect(created?.file?.path).toBe(filePath)
|
|
184
|
+
expect(created?.file?.action).toBe('created')
|
|
185
|
+
|
|
186
|
+
// Overwrite the same file
|
|
187
|
+
const overwritten = await withRetry(
|
|
188
|
+
() => create_file({
|
|
189
|
+
owner: ctx.owner,
|
|
190
|
+
repo: ctx.repo,
|
|
191
|
+
branch: branchName,
|
|
192
|
+
path: filePath,
|
|
193
|
+
content: `Overwritten content at ${timestamp}`,
|
|
194
|
+
message: `Overwrite test file ${timestamp}`,
|
|
195
|
+
}),
|
|
196
|
+
{ maxAttempts: 3, delayMs: 2000 },
|
|
197
|
+
)
|
|
198
|
+
expect(overwritten?.commit?.sha).toBeTruthy()
|
|
199
|
+
expect(overwritten?.file?.action).toBe('overwritten')
|
|
200
|
+
|
|
201
|
+
// Verify content -- retry until the Contents API reflects the overwrite
|
|
202
|
+
const get_file_contents = toolbox.read('get_file_contents')
|
|
203
|
+
const contents = await withRetry(
|
|
204
|
+
async () => {
|
|
205
|
+
const c = await get_file_contents({
|
|
206
|
+
owner: ctx.owner,
|
|
207
|
+
repo: ctx.repo,
|
|
208
|
+
path: filePath,
|
|
209
|
+
ref: branchName,
|
|
210
|
+
})
|
|
211
|
+
if (!c?.content?.includes('Overwritten content'))
|
|
212
|
+
throw new Error('stale content: overwrite not yet visible')
|
|
213
|
+
return c
|
|
214
|
+
},
|
|
215
|
+
{ maxAttempts: 5, delayMs: 1500 },
|
|
216
|
+
)
|
|
217
|
+
expect(contents?.content).toContain('Overwritten content')
|
|
218
|
+
|
|
219
|
+
// delete_file without SHA (auto-fetches it)
|
|
220
|
+
const delete_file = toolbox.write('delete_file')
|
|
221
|
+
const deleted = await delete_file({
|
|
222
|
+
owner: ctx.owner,
|
|
223
|
+
repo: ctx.repo,
|
|
224
|
+
path: filePath,
|
|
225
|
+
message: `Delete test file ${timestamp}`,
|
|
115
226
|
branch: branchName,
|
|
116
227
|
})
|
|
117
|
-
expect(
|
|
118
|
-
|
|
228
|
+
expect(deleted?.commit?.message).toBe(`Delete test file ${timestamp}`)
|
|
229
|
+
|
|
230
|
+
const delete_branch = toolbox.write('delete_branch')
|
|
231
|
+
await delete_branch({ owner: ctx.owner, repo: ctx.repo, branch: branchName })
|
|
232
|
+
}, 120000)
|
|
233
|
+
|
|
234
|
+
it('edit_file: search/replace on a single file', async () => {
|
|
235
|
+
if (!ctx.owner || !ctx.repo)
|
|
236
|
+
return expect(true).toBe(true)
|
|
237
|
+
|
|
238
|
+
const timestamp = Date.now()
|
|
239
|
+
const branchName = `test-edit-file-${timestamp}`
|
|
240
|
+
const filePath = `test-edit-${timestamp}.txt`
|
|
119
241
|
|
|
120
|
-
const
|
|
242
|
+
const create_branch = toolbox.write('create_branch')
|
|
243
|
+
await create_branch({ owner: ctx.owner, repo: ctx.repo, branch: branchName })
|
|
244
|
+
|
|
245
|
+
// Seed a file to edit
|
|
246
|
+
const create_file = toolbox.write('create_file')
|
|
247
|
+
await create_file({
|
|
121
248
|
owner: ctx.owner,
|
|
122
249
|
repo: ctx.repo,
|
|
123
|
-
path: `test-single-${timestamp}.txt`,
|
|
124
|
-
message: `Update test file ${timestamp}`,
|
|
125
|
-
content: `Updated content at ${timestamp}`,
|
|
126
250
|
branch: branchName,
|
|
127
|
-
|
|
251
|
+
path: filePath,
|
|
252
|
+
content: 'line 1: hello world\nline 2: foo bar\nline 3: goodbye world\n',
|
|
253
|
+
message: `Seed file for edit test ${timestamp}`,
|
|
128
254
|
})
|
|
129
|
-
expect(updated?.commit?.message).toBe(`Update test file ${timestamp}`)
|
|
130
|
-
}, 90000)
|
|
131
255
|
|
|
132
|
-
|
|
256
|
+
// Apply search/replace edits
|
|
257
|
+
const edit_file = toolbox.write('edit_file')
|
|
258
|
+
const edited = await withRetry(
|
|
259
|
+
() => edit_file({
|
|
260
|
+
owner: ctx.owner,
|
|
261
|
+
repo: ctx.repo,
|
|
262
|
+
branch: branchName,
|
|
263
|
+
path: filePath,
|
|
264
|
+
edits: [
|
|
265
|
+
{ old_text: 'hello world', new_text: 'hello universe' },
|
|
266
|
+
{ old_text: 'foo bar', new_text: 'baz qux' },
|
|
267
|
+
],
|
|
268
|
+
message: `Edit file ${timestamp}`,
|
|
269
|
+
}),
|
|
270
|
+
{ maxAttempts: 3, delayMs: 2000 },
|
|
271
|
+
)
|
|
272
|
+
expect(edited?.commit?.sha).toBeTruthy()
|
|
273
|
+
expect(edited?.file?.path).toBe(filePath)
|
|
274
|
+
|
|
275
|
+
// Verify edits applied -- retry until the Contents API reflects the new commit
|
|
276
|
+
const get_file_contents = toolbox.read('get_file_contents')
|
|
277
|
+
const contents = await withRetry(
|
|
278
|
+
async () => {
|
|
279
|
+
const c = await get_file_contents({
|
|
280
|
+
owner: ctx.owner,
|
|
281
|
+
repo: ctx.repo,
|
|
282
|
+
path: filePath,
|
|
283
|
+
ref: branchName,
|
|
284
|
+
})
|
|
285
|
+
if (!c?.content?.includes('hello universe'))
|
|
286
|
+
throw new Error('stale content: edit not yet visible')
|
|
287
|
+
return c
|
|
288
|
+
},
|
|
289
|
+
{ maxAttempts: 5, delayMs: 1500 },
|
|
290
|
+
)
|
|
291
|
+
expect(contents?.content).toContain('hello universe')
|
|
292
|
+
expect(contents?.content).toContain('baz qux')
|
|
293
|
+
expect(contents?.content).toContain('goodbye world')
|
|
294
|
+
expect(contents?.content).not.toContain('hello world')
|
|
295
|
+
|
|
296
|
+
const delete_branch = toolbox.write('delete_branch')
|
|
297
|
+
await delete_branch({ owner: ctx.owner, repo: ctx.repo, branch: branchName })
|
|
298
|
+
}, 120000)
|
|
299
|
+
|
|
300
|
+
it('edit_files: mixed create, edit, delete in one atomic commit', async () => {
|
|
133
301
|
if (!ctx.owner || !ctx.repo)
|
|
134
302
|
return expect(true).toBe(true)
|
|
135
303
|
|
|
136
304
|
const timestamp = Date.now()
|
|
137
|
-
const branchName = `test-
|
|
305
|
+
const branchName = `test-edit-files-${timestamp}`
|
|
138
306
|
|
|
139
307
|
const create_branch = toolbox.write('create_branch')
|
|
140
308
|
const branch = await create_branch({ owner: ctx.owner, repo: ctx.repo, branch: branchName })
|
|
141
309
|
expect(branch?.ref).toBe(`refs/heads/${branchName}`)
|
|
142
310
|
|
|
143
|
-
|
|
144
|
-
const
|
|
311
|
+
// Seed initial files via edit_files (create action)
|
|
312
|
+
const edit_files = toolbox.write('edit_files')
|
|
313
|
+
const commit1 = await edit_files({
|
|
145
314
|
owner: ctx.owner,
|
|
146
315
|
repo: ctx.repo,
|
|
147
316
|
branch: branchName,
|
|
148
|
-
message: `Add
|
|
317
|
+
message: `Add initial files ${timestamp}`,
|
|
149
318
|
files: [
|
|
150
|
-
{ path: `multi-test/file1-${timestamp}.txt`, content: 'Content of file 1' },
|
|
151
|
-
{ path: `multi-test/file2-${timestamp}.txt`, content: 'Content of file 2' },
|
|
152
|
-
{ path: `multi-test/file3-${timestamp}.md`, content: '# Test File 3\n\nWith UTF-8: 你好 🚀' },
|
|
319
|
+
{ path: `multi-test/file1-${timestamp}.txt`, action: 'create', content: 'Content of file 1' },
|
|
320
|
+
{ path: `multi-test/file2-${timestamp}.txt`, action: 'create', content: 'Content of file 2' },
|
|
321
|
+
{ path: `multi-test/file3-${timestamp}.md`, action: 'create', content: '# Test File 3\n\nWith UTF-8: 你好 🚀' },
|
|
153
322
|
],
|
|
154
323
|
})
|
|
155
|
-
expect(
|
|
156
|
-
expect(
|
|
157
|
-
expect(
|
|
158
|
-
|
|
159
|
-
|
|
324
|
+
expect(commit1?.commit?.sha).toBeTruthy()
|
|
325
|
+
expect(commit1?.commit?.message).toBe(`Add initial files ${timestamp}`)
|
|
326
|
+
expect(commit1?.files?.length).toBe(3)
|
|
327
|
+
|
|
328
|
+
// Mixed operations: edit file1, delete file2, create file4
|
|
329
|
+
const commit2 = await withRetry(
|
|
330
|
+
() => edit_files({
|
|
331
|
+
owner: ctx.owner,
|
|
332
|
+
repo: ctx.repo,
|
|
333
|
+
branch: branchName,
|
|
334
|
+
message: `Mixed edit/delete/create ${timestamp}`,
|
|
335
|
+
files: [
|
|
336
|
+
{
|
|
337
|
+
path: `multi-test/file1-${timestamp}.txt`,
|
|
338
|
+
action: 'edit',
|
|
339
|
+
edits: [{ old_text: 'Content of file 1', new_text: 'Updated content of file 1' }],
|
|
340
|
+
},
|
|
341
|
+
{ path: `multi-test/file2-${timestamp}.txt`, action: 'delete' },
|
|
342
|
+
{ path: `multi-test/file4-${timestamp}.txt`, action: 'create', content: 'New file 4' },
|
|
343
|
+
],
|
|
344
|
+
}),
|
|
345
|
+
{
|
|
346
|
+
maxAttempts: 3,
|
|
347
|
+
delayMs: 2000,
|
|
348
|
+
retryIf: (e: unknown) => String((e as { message?: string })?.message || '').includes('GitRPC::BadObjectState'),
|
|
349
|
+
},
|
|
350
|
+
)
|
|
351
|
+
expect(commit2?.commit?.sha).toBeTruthy()
|
|
352
|
+
expect(commit2?.files?.length).toBe(3)
|
|
353
|
+
|
|
354
|
+
// Verify the edit applied -- retry until the Contents API reflects the new commit
|
|
355
|
+
const get_file_contents = toolbox.read('get_file_contents')
|
|
356
|
+
const f1 = await withRetry(
|
|
357
|
+
async () => {
|
|
358
|
+
const c = await get_file_contents({
|
|
359
|
+
owner: ctx.owner,
|
|
360
|
+
repo: ctx.repo,
|
|
361
|
+
path: `multi-test/file1-${timestamp}.txt`,
|
|
362
|
+
ref: branchName,
|
|
363
|
+
})
|
|
364
|
+
if (!c?.content?.includes('Updated content of file 1'))
|
|
365
|
+
throw new Error('stale content: edit not yet visible')
|
|
366
|
+
return c
|
|
367
|
+
},
|
|
368
|
+
{ maxAttempts: 5, delayMs: 1500 },
|
|
369
|
+
)
|
|
370
|
+
expect(f1?.content).toContain('Updated content of file 1')
|
|
371
|
+
|
|
372
|
+
// Verify the new file was created
|
|
373
|
+
const f4 = await get_file_contents({
|
|
160
374
|
owner: ctx.owner,
|
|
161
375
|
repo: ctx.repo,
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
files: [
|
|
165
|
-
{ path: `multi-test/file1-${timestamp}.txt`, content: 'Updated content of file 1' },
|
|
166
|
-
{ path: `multi-test/file2-${timestamp}.txt` },
|
|
167
|
-
{ path: `multi-test/file4-${timestamp}.txt`, content: 'New file 4' },
|
|
168
|
-
],
|
|
376
|
+
path: `multi-test/file4-${timestamp}.txt`,
|
|
377
|
+
ref: branchName,
|
|
169
378
|
})
|
|
170
|
-
expect(
|
|
171
|
-
|
|
172
|
-
|
|
379
|
+
expect(f4?.content).toContain('New file 4')
|
|
380
|
+
|
|
381
|
+
// get_commit verifies the commit details
|
|
382
|
+
const get_commit = toolbox.read('get_commit')
|
|
383
|
+
const commitDetails = await get_commit({ owner: ctx.owner, repo: ctx.repo, sha: commit2.commit.sha })
|
|
384
|
+
expect(commitDetails?.sha).toBe(commit2.commit.sha)
|
|
385
|
+
}, 150000)
|
|
173
386
|
|
|
174
|
-
it('full PR workflow: create_branch ->
|
|
387
|
+
it('full PR workflow: create_branch -> edit_files -> create_pull_request -> update_pull_request -> create_pull_request_review -> merge_pull_request -> delete_branch', async () => {
|
|
175
388
|
if (!ctx.owner || !ctx.repo)
|
|
176
389
|
return expect(true).toBe(true)
|
|
177
390
|
|
|
@@ -182,15 +395,15 @@ suiteOrSkip('github write handlers (live)', () => {
|
|
|
182
395
|
const branch = await create_branch({ owner: ctx.owner, repo: ctx.repo, branch: branchName })
|
|
183
396
|
expect(branch?.ref).toBe(`refs/heads/${branchName}`)
|
|
184
397
|
|
|
185
|
-
const
|
|
186
|
-
const commit = await
|
|
398
|
+
const edit_files = toolbox.write('edit_files')
|
|
399
|
+
const commit = await edit_files({
|
|
187
400
|
owner: ctx.owner,
|
|
188
401
|
repo: ctx.repo,
|
|
189
402
|
branch: branchName,
|
|
190
403
|
message: `Add feature files ${timestamp}`,
|
|
191
404
|
files: [
|
|
192
|
-
{ path: `feature-${timestamp}/index.js`, content: 'export default function() { return "Hello"; }' },
|
|
193
|
-
{ path: `feature-${timestamp}/README.md`, content: `# Feature ${timestamp}\n\nThis is a test feature.` },
|
|
405
|
+
{ path: `feature-${timestamp}/index.js`, action: 'create', content: 'export default function() { return "Hello"; }' },
|
|
406
|
+
{ path: `feature-${timestamp}/README.md`, action: 'create', content: `# Feature ${timestamp}\n\nThis is a test feature.` },
|
|
194
407
|
],
|
|
195
408
|
})
|
|
196
409
|
expect(commit?.commit?.sha).toBeTruthy()
|
|
@@ -211,6 +424,27 @@ suiteOrSkip('github write handlers (live)', () => {
|
|
|
211
424
|
expect(pr?.number).toBeTruthy()
|
|
212
425
|
const prNumber = pr.number
|
|
213
426
|
|
|
427
|
+
// update_pull_request
|
|
428
|
+
const update_pull_request = toolbox.write('update_pull_request')
|
|
429
|
+
const updated = await update_pull_request({
|
|
430
|
+
owner: ctx.owner,
|
|
431
|
+
repo: ctx.repo,
|
|
432
|
+
pull_number: prNumber,
|
|
433
|
+
body: 'Updated description by integration test.',
|
|
434
|
+
})
|
|
435
|
+
expect(updated?.number).toBe(prNumber)
|
|
436
|
+
|
|
437
|
+
// get_pull_request verifies state
|
|
438
|
+
const get_pull_request = toolbox.read('get_pull_request')
|
|
439
|
+
const prDetails = await get_pull_request({ owner: ctx.owner, repo: ctx.repo, pull_number: prNumber })
|
|
440
|
+
expect(prDetails?.number).toBe(prNumber)
|
|
441
|
+
|
|
442
|
+
// list_pull_request_files
|
|
443
|
+
const list_pull_request_files = toolbox.read('list_pull_request_files')
|
|
444
|
+
const files = await list_pull_request_files({ owner: ctx.owner, repo: ctx.repo, pull_number: prNumber })
|
|
445
|
+
expect(Array.isArray(files)).toBe(true)
|
|
446
|
+
|
|
447
|
+
// add_labels_to_issue (labels on PR)
|
|
214
448
|
const add_labels_to_issue = toolbox.write('add_labels_to_issue')
|
|
215
449
|
try {
|
|
216
450
|
await add_labels_to_issue({ owner: ctx.owner, repo: ctx.repo, issue_number: prNumber, labels: ['test'] })
|
|
@@ -219,9 +453,43 @@ suiteOrSkip('github write handlers (live)', () => {
|
|
|
219
453
|
// Label might not exist -- that's ok for this test
|
|
220
454
|
}
|
|
221
455
|
|
|
456
|
+
// request_pull_request_reviewers (may fail if requesting from self)
|
|
457
|
+
const request_pull_request_reviewers = toolbox.write('request_pull_request_reviewers')
|
|
458
|
+
try {
|
|
459
|
+
await request_pull_request_reviewers({
|
|
460
|
+
owner: ctx.owner,
|
|
461
|
+
repo: ctx.repo,
|
|
462
|
+
pull_number: prNumber,
|
|
463
|
+
reviewers: [],
|
|
464
|
+
})
|
|
465
|
+
}
|
|
466
|
+
catch {
|
|
467
|
+
// May fail if requesting from self or insufficient permissions -- that's ok
|
|
468
|
+
}
|
|
469
|
+
|
|
470
|
+
// create_pull_request_review (comment only -- can't APPROVE own PRs typically)
|
|
471
|
+
const create_pull_request_review = toolbox.write('create_pull_request_review')
|
|
472
|
+
try {
|
|
473
|
+
await create_pull_request_review({
|
|
474
|
+
owner: ctx.owner,
|
|
475
|
+
repo: ctx.repo,
|
|
476
|
+
pull_number: prNumber,
|
|
477
|
+
event: 'COMMENT',
|
|
478
|
+
body: 'LGTM from integration test',
|
|
479
|
+
})
|
|
480
|
+
}
|
|
481
|
+
catch {
|
|
482
|
+
// May fail if author is same as reviewer in some repo configs -- that's ok
|
|
483
|
+
}
|
|
484
|
+
|
|
222
485
|
const merge_pull_request = toolbox.write('merge_pull_request')
|
|
223
486
|
const merged = await merge_pull_request({ owner: ctx.owner, repo: ctx.repo, pull_number: prNumber, merge_method: 'squash' })
|
|
224
487
|
expect(merged?.merged).toBe(true)
|
|
488
|
+
|
|
489
|
+
// delete_branch after merge
|
|
490
|
+
const delete_branch = toolbox.write('delete_branch')
|
|
491
|
+
const deletedBranch = await delete_branch({ owner: ctx.owner, repo: ctx.repo, branch: branchName })
|
|
492
|
+
expect(deletedBranch?.success).toBe(true)
|
|
225
493
|
}, 150000)
|
|
226
494
|
})
|
|
227
495
|
}
|
|
@@ -11,17 +11,25 @@ async (input) => {
|
|
|
11
11
|
const commitData = await commitRes.json()
|
|
12
12
|
const currentTreeSha = commitData.tree.sha
|
|
13
13
|
|
|
14
|
-
// 3. Build tree entries
|
|
14
|
+
// 3. Build tree entries.
|
|
15
|
+
// Always create blobs explicitly rather than using inline tree content, because mixing inline
|
|
16
|
+
// content with sha:null deletion entries in the same tree request causes GitRPC::BadObjectState.
|
|
15
17
|
const tree = []
|
|
16
18
|
for (const file of files) {
|
|
17
19
|
if (file.content !== undefined && file.content !== null) {
|
|
20
|
+
const blobRes = await integration.fetch(`/repos/${owner}/${repo}/git/blobs`, {
|
|
21
|
+
method: 'POST',
|
|
22
|
+
body: { content: file.content, encoding: 'utf-8' },
|
|
23
|
+
})
|
|
24
|
+
const blobData = await blobRes.json()
|
|
18
25
|
tree.push({
|
|
19
26
|
path: file.path,
|
|
20
27
|
mode: file.mode || '100644',
|
|
21
28
|
type: 'blob',
|
|
22
|
-
|
|
29
|
+
sha: blobData.sha,
|
|
23
30
|
})
|
|
24
31
|
} else {
|
|
32
|
+
// sha: null removes the file from the tree
|
|
25
33
|
tree.push({
|
|
26
34
|
path: file.path,
|
|
27
35
|
mode: '100644',
|
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
async (input) => {
|
|
2
|
+
const { owner, repo, branch, path, content, message } = input
|
|
3
|
+
|
|
4
|
+
// Check if the file already exists to get its SHA for overwrite
|
|
5
|
+
let existingSha
|
|
6
|
+
try {
|
|
7
|
+
const params = new URLSearchParams()
|
|
8
|
+
params.set('ref', branch)
|
|
9
|
+
const checkRes = await integration.fetch(`/repos/${owner}/${repo}/contents/${path}?${params.toString()}`)
|
|
10
|
+
const checkData = await checkRes.json()
|
|
11
|
+
if (checkData && checkData.sha) {
|
|
12
|
+
existingSha = checkData.sha
|
|
13
|
+
}
|
|
14
|
+
} catch (e) {
|
|
15
|
+
// 404 means file doesn't exist yet -- that's fine
|
|
16
|
+
}
|
|
17
|
+
|
|
18
|
+
const contentBase64 = btoa(unescape(encodeURIComponent(content)))
|
|
19
|
+
|
|
20
|
+
const body = {
|
|
21
|
+
message: message,
|
|
22
|
+
content: contentBase64,
|
|
23
|
+
branch: branch,
|
|
24
|
+
}
|
|
25
|
+
if (existingSha) {
|
|
26
|
+
body.sha = existingSha
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
const res = await integration.fetch(`/repos/${owner}/${repo}/contents/${path}`, {
|
|
30
|
+
method: 'PUT',
|
|
31
|
+
body: body,
|
|
32
|
+
})
|
|
33
|
+
const result = await res.json()
|
|
34
|
+
|
|
35
|
+
return {
|
|
36
|
+
commit: {
|
|
37
|
+
sha: result.commit?.sha,
|
|
38
|
+
message: result.commit?.message,
|
|
39
|
+
url: result.commit?.html_url,
|
|
40
|
+
},
|
|
41
|
+
file: {
|
|
42
|
+
path: path,
|
|
43
|
+
action: existingSha ? 'overwritten' : 'created',
|
|
44
|
+
},
|
|
45
|
+
}
|
|
46
|
+
}
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
async (input) => {
|
|
2
|
+
const body = { event: input.event }
|
|
3
|
+
if (input.body !== undefined) body.body = input.body
|
|
4
|
+
if (input.commit_id !== undefined) body.commit_id = input.commit_id
|
|
5
|
+
const res = await integration.fetch(
|
|
6
|
+
`/repos/${input.owner}/${input.repo}/pulls/${input.pull_number}/reviews`,
|
|
7
|
+
{ method: 'POST', body }
|
|
8
|
+
)
|
|
9
|
+
return await res.json()
|
|
10
|
+
}
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
async (input) => {
|
|
2
|
+
const body = { tag_name: input.tag_name }
|
|
3
|
+
if (input.name !== undefined) body.name = input.name
|
|
4
|
+
if (input.body !== undefined) body.body = input.body
|
|
5
|
+
if (input.draft !== undefined) body.draft = input.draft
|
|
6
|
+
if (input.prerelease !== undefined) body.prerelease = input.prerelease
|
|
7
|
+
if (input.target_commitish !== undefined) body.target_commitish = input.target_commitish
|
|
8
|
+
if (input.generate_release_notes !== undefined) body.generate_release_notes = input.generate_release_notes
|
|
9
|
+
const res = await integration.fetch(
|
|
10
|
+
`/repos/${input.owner}/${input.repo}/releases`,
|
|
11
|
+
{ method: 'POST', body }
|
|
12
|
+
)
|
|
13
|
+
return await res.json()
|
|
14
|
+
}
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
async (input) => {
|
|
2
|
+
let sha = input.sha
|
|
3
|
+
if (!sha) {
|
|
4
|
+
const params = new URLSearchParams()
|
|
5
|
+
if (input.branch) params.set('ref', input.branch)
|
|
6
|
+
const query = params.toString() ? `?${params.toString()}` : ''
|
|
7
|
+
const fileRes = await integration.fetch(`/repos/${input.owner}/${input.repo}/contents/${input.path}${query}`)
|
|
8
|
+
const fileData = await fileRes.json()
|
|
9
|
+
if (!fileData || !fileData.sha) {
|
|
10
|
+
throw new Error(`File not found: ${input.path}. Cannot delete a file that does not exist.`)
|
|
11
|
+
}
|
|
12
|
+
sha = fileData.sha
|
|
13
|
+
}
|
|
14
|
+
|
|
15
|
+
const body = { message: input.message, sha: sha }
|
|
16
|
+
if (input.branch) body.branch = input.branch
|
|
17
|
+
const res = await integration.fetch(
|
|
18
|
+
`/repos/${input.owner}/${input.repo}/contents/${input.path}`,
|
|
19
|
+
{ method: 'DELETE', body }
|
|
20
|
+
)
|
|
21
|
+
return await res.json()
|
|
22
|
+
}
|