Prepare an Extension for Store
Learn how to get through review process quickly
Here you will find requirements and guidelines that you'll need to follow in order to get through the review before your extension becomes available in the Store. Please read it carefully because it will save time for you and for us. This document is constantly evolving so please do visit it from time to time.
- Things to double-check in your
- Ensure you use your Raycast account username in the
- Ensure you use
- Ensure you are using the latest Raycast API version
- Please use
npmfor installing dependencies and include
package-lock.jsonin your pull request. We use
npmon our Continuous Integration (CI) environment when building and publishing extensions so, by providing a
package-lock.jsonfile, we ensure that the dependencies on the server match the same versions as your local dependencies.
- Please check the terms of service of third-party services that your extension uses. If your extension doesn't comply with their terms, include a warning in your extension's README. The warning should be similar to:Warning: This extension is not compliant with the Terms of Service of [service name]. Use at your own risk.
- Make sure to run a distribution build with
npm run buildlocally before submitting the extension for review. This will perform additional type checking and create an optimized build. Open the extension in Raycast to check whether everything works as expected with the distribution build. In addition, you can perform linting and code style checks by running
npm run lint. (Those checks will later also run via automated GitHub checks.)
- Extension and command titles should follow Apple Style Guide convention
Doppler Share Secrets,
Search in Database
- 🤔 It's okay to use lower case for names and trademarks that are canonically written with lower case letters. E.g.
- Extension title
- It will be used only in the Store and in the preferences
- Make it easy for people to understand what it does when they see it in the Store
Airport - Discover Testflight Apps,
- 🤔 In some cases, you can add additional information to the title similar to the Airport example above. Only do so if it adds context.
- 💡 You can use more creative titles to differentiate your extension from other extensions with similar names.
- Aim to use nouns rather than verbs
Emoji Searchis better than
- Avoid generic names for an extension when your extension doesn't provide a lot of commands
- E.g. if your extension can only search pages in Notion, name it
Notion Searchinstead of just
Notion. This will help users to form the right expectations about your extension. If your extension covers a lot of functionality, it's okay to use a generic name like
Notion. Example: GitLab.
- Rule of thumb: If your extension has only one command, you probably need to name the extension close to what this command does. Example: Visual Studio Code Recent Projects instead of just
Visual Studio Code.
- Extension description
- In one sentence, what does your extension do? This will be shown in the list of extensions in the Store. Keep it short and descriptive. See how other approved extensions in the Store do it for inspiration.
- Command title
- Usually it's
<verb> <noun>structure or just
- The best approach is to see how other commands are named in Raycast to get inspiration
Search Recent Projects,
Recent Projects Search,
- Avoid articles
Search an Emoji,
Create an Issue
- Avoid just giving it a service name, be more specific about what the command does
- Command subtitle
- Use subtitles to add context to your command. Usually, it's an app or service name that you integrate with. It makes command names more lightweight and removes the need to specify a service name in the command title.
- The subtitle is indexed so you can still search using subtitle and title:
xcode recent projectswould return
Search Recent Projectsin the example above.
- Don't use subtitles as descriptions for your command
Quickly open Xcode recent projects
- Don't use a subtitle if it doesn't add context. Usually, this is the case with single command extensions.
- There is no need for a subtitle for the
Search Emojicommand since it's self-explanatory
- Rule of thumb: If your subtitle is almost a duplication of your command title, you probably don't need it
Example of a good subtitle
- The published extension in the Store should have a 512x512px icon in
- The icon should look good in both light and dark themes (you can switch the theme in Raycast Preferences → Appearance)
- Extensions that use the default Raycast icon will be rejected
- Make sure to remove unused assets and icons
- If your extension requires additional setup, such as getting an API access token, enabling some preferences in other applications, or has non-trivial use cases, please provide a README file at the root folder of your extension. When a README is provided, users will see the "About This Extension" button on the preferences onboarding screen.
- Supporting README media: Put all linked media files in a top-level
mediafolder inside your extension directory. (This is different from assets that are required at runtime in your extension: they go inside the assets folder and will be bundled into your extension.)
Onboarding button linking to the README file
Categories shown on an extension details screen
- All extensions should be published with at least one category
An example of an extension with screenshot metadata
- Screenshots are displayed in the metadata of an extension details screen, where users can click and browse through them to understand what your extension does in greater detail, before installing
- You can add a maximum of six screenshots. We recommend adding at least three, so your extensions detail screen looks beautiful.
In Raycast 1.37.0+ we made it easy for you to take beautiful pixel perfect screenshots of your extension with an ease.
- 1.Set up Window Capture in Advanced Preferences (Hotkey e.g.:
- 2.Open the command
- 3.Press the hotkey, remember to tick
Save to Metadata
- ✅ Choose a background with good contrast, that makes it clear and easy to see the app and extension you’ve made
- ✅ Select the most informative commands to showcase what your extension does – focus on giving the user as much detail as possible
- ❌ Do not use multiple backgrounds for different screenshots – be consistent and use the same across all screenshots
- ❌ Do not share sensitive data in your screenshots – these will be visible in the Store, as well as the Extension repository on GitHub
- ❌ Avoid using screenshots in different themes (light and dark), unless it is to demonstrate what your extension does
A CHANGELOG.md file displayed in the app
- Make it easier for users to see exactly what notable changes have been made between each release of your extension with a
CHANGELOG.mdfile in your extension metadata
- To add Version History to your extension, add a
CHANGELOG.mdfile to the root folder of your extension
- With each change, provide clear and descriptive information around the latest update, providing a title as a h2 header followed by a date timestamp YYYY-MM-DD
- Make sure your change title is within square brackets
- Separate your title and date with a hyphen
-and spaces either side of the hyphen
- Below is an example of a changelog that follows the correct format
# Brew Changelog
## [Added a bunch of new feedback] - 2022-01-17
- Improve reliability of `outdated` command
- Add action to copy formula/cask name
- Add cask name & tap to cask details
- Add Toast action to cancel current action
- Add Toast action to copy error log after failure
## [New Additions] - 2022-12-13
- Add greedy upgrade preference
- Add `upgrade` command
## [Fixes & Bits] - 2021-11-19
- Improve discovery of brew prefix
- Update Cask.installed correctly after installation
- Fix installed state after uninstalling search result
- Fix cache check after installing/uninstalling cask
- Add uninstall action to outdated action panel
## [New Commands] - 2021-11-04
Add support for searching and managing casks
## [Added Brew] - 2021-10-26
Initial version code
An extensions version history on raycast.com/store
- When you should contribute to an existing extension instead of creating a new one
- You want to make a small improvement to an extension that is already published, e.g. extra actions, new preference, UX improvements, etc.. Usually, it's a non-significant change.
- You want to add a simple command that compliments an existing extension without changing the extension title or description, e.g. you want to add "Like Current Track" command for Spotify. It wouldn't make sense to create a whole new extension just for this when there is already the Spotify Controls extension.
- Important: If your change is significant, it makes sense to contact the author of the extension before you invest a lot of time into it. We cannot merge significant contributions without the author's sign-off.
- When you should consider creating a new extension instead of contributing to an existing one
- The changes to an existing extension would be significant and might break other people's workflows. Check with the author if you want to proceed with the collaboration path.
- Your extension provides an integration with the same service but has a different configuration, e.g. one extension could be "GitHub Cloud", another "GitHub Enterprise". One extension could be "Spotify Controls" and only uses AppleScript to play/pause songs, while another extension can provide deeper integration via the API and require an access token setup. There is no reason to try to merge everything together as this would only make things more complicated.
- Multiple simple extensions vs one large one
- If your extension works standalone and brings something new to the Store, it's acceptable to create a new one instead of adding commands to an existing one. E.g. one extension could be "GitHub Repository Search", another one could be "GitHub Issue Search". It should not be the goal to merge all extensions connecting with one service into one mega extension. However, it's also acceptable to merge two extensions under one if the authors decide to do so.
- Avoid asking users to perform additional downloads and try to automate as much as possible from the extension, especially if you are targeting non-developers. See the Speedtest extension that downloads a CLI in the background and later uses it under the hood.
- If you do end up downloading executable binaries in the background, please make sure it's done from a server that you don't have access to. Otherwise, we cannot guarantee that you won't replace the binary with malicious code after the review. E.g. downloading
install.speedtest.netis acceptable, but doing this from some custom AWS server would lead to a rejection. Add additional integrity checks through hashes.
- Don't bundle opaque binaries where sources are unavailable or where it's unclear how they have been built.
- Don't bundle heavy binary dependencies in the extension – this would lead to an increased extension download size.
- Examples for interacting with binaries
- ✅ Calling known system binaries
- ✅ Binary downloaded or installed from a trusted location with additional integrity checking through hashes (that is, verify whether the downloaded binary really matches the expected binary)
- ✅ Binary extracted from an npm package and copied to assets, with traceable sources how the binary is built; note: we have yet to integrate CI actions for copying and comparing the files; meanwhile, ask a member of the Raycast team to add the binary for you
- ❌ Any binary with unavailable sources or unclear builds just added to the assets folder
Required preferences will be shown when opening the command
Raycast Action Panel component
- Actions in the action panel should also follow the Title Case naming convention
Open in Browser,
Copy to Clipboard
- Provide icons for actions if there are other actions with icons in the list
- Avoid having a list of actions where some have icons and some don't
- Add ellipses
...for actions that will have a submenu. Don't repeat parent the action name in the submenu
Set Priority...and submenu would have
Set Priorityand submenu would have
Set Priority Low,
Set Priority Medium, etc
- Avoid introducing your own navigation stack. Extensions that just replace the view's content when it's expected to push a new screen will be rejected.
- When you update lists with an empty array of elements, the "No results" view will be shown. Avoid introducing your own UI to achieve a similar effect (e.g. showing list item).
- Known issue: Sometimes, there is nothing you can show when the search query is empty, and an extension shows "No results" when you open it (often in search commands). We have plans to provide an API that would improve that experience. In the meantime, you might want to consider introducing some sections that could be helpful in an empty state – e.g. suggestions or recently visited items.
- Common mistake – "flickering empty state view" on start
- If you try rendering an empty list before real data arrives (e.g. from the network or disk), you might see a flickering "No results" view when opening the extension. To prevent this, make sure not to return an empty list of items before you get the data you want to display. In the meantime, you can show the loading indicator. See this example.
- Don't change the
navigationTitlein the root command - it will be automatically set to the command name. Use
navigationTitleonly in nested screens to provide additional context. See Slack Status extension as an example of correct usage of the
- Avoid long titles. If you can't predict how long the navigation title string will be, consider using something else. E.g. in the Jira extension, we use the issue key instead of the issue title to keep it short.
- Avoid updating the navigation title multiple times on one screen depending on some state. If you find yourself doing it, there is a high chance you are misusing it.
- For a better visual experience, add placeholders in text field and text area components. This includes preferences.
- Don't leave the search bar without a placeholder
- It’s not allowed to include external analytics in extensions. Later on, we will add support to give developers more insights into how their extension is being used.
- At the moment, Raycast doesn't support localization and only supports US English. Therefore, please avoid introducing your custom way to localize your extension. If the locale might affect functionality (e.g. using the correct unit of measurement), please use the preferences API.
- Use US English spelling (not British)