Dart posted on Hacker News and is live on Launch YC today only—check it out!

How to Make a Great ChatGPT Plugin

emmanuel-acquah
Emmanuel Acquah
June 19, 2023
15
minute read

This is part of a two-part series about my experience making a ChatGPT plugin at Dart. In addition to this post, check out the other about What I learned from making a top ChatGPT plugin.

How to make a great ChatGPT plugin

I was lucky enough to get very early access to be a ChatGPT plugin developer since our product is very AI-oriented, and as a result I am in close contact with OpenAI. This post is about how to make your very own ChatGPT plugin.

ChatGPT and its plugins are so new that the existing guides still need some work, so I thought this could help you if you’re trying to make your own plugin. Even OpenAI’s documentation, while pretty good, is evolving quickly and misses some details and practical things you need to know.

The general process is doable, but there are some gotchas along the way. You need to get access to plugins, become a plugin developer, develop the plugin, and then submit the plugin for review. You might need to iterate some during the review process, and you will probably want to iterate afterward to keep improving your app.

Let’s get started!

Get access to ChatGPT plugins as a user

To do this, you’ll need to

  1. Subscribe to ChatGPT Plus ($20/month) by clicking your name in the bottom left, then selecting ‘My plan'
  2. Ensure you have plugins enabled by clicking your name in the bottom left, then selecting 'Settings' -> 'Beta features' and ensure 'Plugins' are on
  3. If there is an option for it, enable two-factor authentication (TFA) in 'Settings' -> 'Data controls'

Once all of this is set up, you should be able to start a new chat, set the model to GPT-4, then hover over the slider and choose to enable plugins (this interaction is not that intuitive). You can pick from the existing plugins and enable one (like Dart) to ensure it works.

Every developer that is going to work on the project will need to do this separately. In theory, you could also set up a shared account to save money and simplify things, although this may be against OpenAI’s terms of service.

OpenAI and ChatGPT have been building so fast that they have broken some things, and there are some mysterious discrepancies between different people’s accounts. For example, I still can’t access TFA in my settings. Other developers I have worked with do have access to TFA and had to turn it on to do some development steps.

Become a ChatGPT plugin developer

As of now this may be the hardest part. I assume that they will probably make it a lot easier soon. The first step is to fill out this form; then, I recommend working directly with the OpenAI team to get access. If you have a support rep with OpenAI, you could email them or go through the help center. You could also become active on the plugin developer forum and ask about it there!

Once you have access, your plugin store will look more like this—note the ‘Install an unverified plugin’ and ‘Develop your own plugin’ options in the bottom right.

Start making your very own ChatGPT plugin

In some ways, this is the easy part—it’s just development work!

The OpenAI docs on this part are excellent, so you should look at those. If you are the kind of developer that likes to dive right in, check out this quickstart repo for some code you can use directly.

In short, your steps here are

  1. Make or identify an existing REST API you’d like to expose to ChatGPT
  2. Set up a basic {%cl%}/.well-known/ai-plugin.json{%cle%} file for your application like the example below
  3. {%cb l='json'%}{
       "schema_version": "v1",
       "name_for_human": "TODO List (No Auth)",
       "name_for_model": "todo",
       "description_for_human": "Manage your TODO list. You can add, remove and view your TODOs.",
       "description_for_model": "Plugin for managing a TODO list, you can add, remove and view your TODOs.",
       "auth": {
           "type": "none"
       },
       "api": {
           "type": "openapi",
           "url": "PLUGIN_HOSTNAME/openapi.yaml"
       },
       "logo_url": "PLUGIN_HOSTNAME/logo.png",
       "contact_email": "support@example.com",
       "legal_info_url": "<https://example.com/legal>"
    }{%cbe%}
  4. Write an OpenAPI spec for your API (automate this if you can—there are a lot of good tools to take an API and make an OpenAPI spec, then you just have to add in some details)

Then you can give it a test and see how it works! To do this, open the plugin store, click ‘Develop your own plugin’, then enter the domain where the API, AI plugin file, and OpenAPI spec are hosted.

One funny thing to note is the close similarity between OpenAI and OpenAPI! I have been in a few conversations where this has gotten confusing. Remember to add the ‘P’ when discussing the API spec format.

While you are making your API, here are some tips to think about

  1. ChatGPT will automatically retry requests based on your error messages, so give excellent error messages. For instance, include all of the errors that come up, and use complete statements with next steps like {%cl%}Invalid value "A". Valid values are "B", "C", or "D"{%cle%}.
  2. ChatGPT is a language model, so make your API more conversational. For example, being descriptive and explaining errors is more important than being consistent with programmatically formatted error messages.
  3. Strive for case insensitivity where possible—I have seen the model mess up casing on field names, for instance, and it is better to handle this in stride if possible.

Authenticate your API

If your service or API requires users to log in to access personal data (like Dart), then you’ll need users to be able to log in to their accounts in your app and link those to their ChatGPT accounts. You should skip this section if your API only has general information that anyone can access.

The best way to do authentication is through OAuth. This is one of the more complicated parts of the process, but it is still not too bad.

If you don’t know much about OAuth2, you might want to read about it here. In particular, pay attention to setting up a new application and the actual authentication request flow because these are the steps you will need to be familiar with for this process.

Set up OAuth2 flow in your app

Make sure your application supports OAuth. I strongly recommend finding a provider that will work with your existing backend if it doesn't already. For instance, since my application is in Django, I used django-oauth-toolkit to accelerate development.

If you can’t find an equivalent option for your backend, you can also consider using a third-party hosted solution like auth0, and if all else fails, you can implement your own set of endpoints that serve the needed requests and responses.

Take note of what format your API expects (e.g., JSON or XML) for the undocumented {%cl%}authorization_content_type{%cle%} option in the next step.

Change your AI plugin file to require OAuth

This is the most straightforward part! Just update your {%cl%}ai-plugin.json{%cle%} file according to the necessary format.

{%cb l='json'%}"auth": {
 "type": "oauth",
 "client_url": "[DOMAIN]/authorize",
 "scope": "",
 "authorization_url": "[DOMAIN]/auth/",
 "authorization_content_type": "application/json",
 "verification_tokens": {
   "openai": "[VERIFICATION_TOKEN]"
 }
},{%cbe%}

It would be best if you parametrized the {%cl%}DOMAIN{%cle%} and {%cl%}VERIFICATION_TOKEN{%cle%} values to be injected by your backend based on the domain and an environment variable, respectively. This will make your life much easier when switching between different environments and iterating on the app.

Get your app on the public internet and using HTTPS

Until now, you could have done all your development on localhost with HTTP. However, to proceed with OAuth, your app must be publicly accessible and served with HTTPS. This can be a little complicated if you are still trying to develop your app quickly because deployment can slow down iteration.

There are a few possibilities:

  1. Use a proxy like ngrok to get your local server on a secure public URL. This is the best option for development but also one of the most complex to initially configure. For ngrok, for instance, you need to upgrade to a paid plan to get a static URL and skip the splash page (ChatGPT won’t like it when it tries to load {%cl%}ai-plugin.json{%cle%} and gets the splash page instead).
  2. Deploy quickly with something like Netlify. Iteration with prod will still take time, but Netfliy can get something from local to deployed within a minute, depending on your build process.
  3. Run your existing build process to a staging or preview environment with slower iteration.

Make a new OAuth application for ChatGPT in your service and register that with ChatGPT

  1. Depending on your setup, how you make the application will vary. Ultimately, you will have an application-specific Client ID and Secret that you should note. I recommend storing them in a password manager because you will need them every time you refresh your app with ChatGPT.
  2. Go back through the Plugin store > ‘Develop your own plugin’ flow and paste in your credentials.
  3. Please note the verification token (also good to save somewhere) and then put it into your AI plugin file or the environment variable that feeds it.
  4. Once this is done, verify the token.

Now, you can test the entire login flow by installing the app into a chat and then clicking the ‘Log in’ button. If everything is correct, it will redirect to your app, you will click authorize, then it will redirect back and begin the chat with you logged in to your app.

Congratulations! You’re mostly done with developing your app!

Some tips for ChatGPT plugin development

There are many little things to pay attention to during this process. Here are some of the things that helped me out the most while I was making my plugin.

  1. Start as basic as possible. Once your app is approved, you can start iterating, so there is no need to go wild initially. You can start by making only one or two endpoints and getting those approved. Then add more functionality later!
  2. The only thing that needs to be relatively ‘final’ when you first submit is your {%cl%}ai-plugin.json{%cle%} file because if you iterate on that, you will need to get the app reapproved.
  3. Automate wherever possible—my backend is in Python, Django, and DRF, so I used django-oauth-toolkit to help with OAuth significantly. I also used drf-spectacular to autogenerate most of the OpenAPI information.
  4. You can check if your OpenAPI spec is valid with an online editor like this one. This can be helpful if you are writing the spec by hand (or even refining some details by hand) because it can be hard to get the format just right.
  5. Make a deployed staging version of your app that you don’t submit but that you can still use for testing! This is good practice in general.
  6. If you can, parametrize some parts of your {%cl%}ai-plugin.json{%cle%} file because they will change a lot during development. In particular, if you use OAuth, you must change your {%cl%}auth.verification_tokens.openai{%cle%} value a few times, so injecting that value from an environment variable rather than hardcoding in your source is helpful!

I hope this helps—if you have other tips that might help others, shoot me a message at blogger@itsdart.com, and I’ll add them in.

Submit your ChatGPT plugin for review

Be sure to give all of the details of your app a once-over before submitting it so that it is more likely to get in on the first try.

  1. Ensure that your {%cl%}ai-plugin.json{%cle%} manifest follows the type description here
  2. One undocumented requirement of the manifest is that both {%cl%}description_for_human{%cle%} and {%cl%}description_for_model{%cle%} end in a period
  3. Make sure that your OpenAPI file is valid, for example, by pasting it into this editor
  4. Check compliance with the brand guidelines
  5. Make sure you follow the content policy
  6. Check the pre-submission checklist
  7. Validate the UX of the login flow, if applicable. Make sure that it is easy to sign up and log in, including carrying the intent to authorize ChatGPT through any of these flows

Once your plugin is ready, you can submit it through this bot. They say they should get back to you in a week or less, but in my experience, it took a little longer and required some pestering. You can send reminders through the same means I mentioned earlier, like the forum, your support rep, etc.

If they get back to you with any issues, you will need to

  1. Fix the issues
  2. Resubmit the domain to ChatGPT with the Plugin store > ‘Develop your own plugin’ flow
  3. Let them know through the chatbot that you have fixed the issue (I recommend including plenty of detail in what you tell the bot so they know what you fixed)
  4. Pester them again

Iterate on your plugin

Once your plugin is approved and in the store, you can improve it. It would be best to listen to your users' feedback and then make changes to make it even better.

You can change your API and OpenAPI spec doc whenever you want, but if you need to change your AI plugin file, you’ll sadly need to resubmit the app for a re-review. However, that’s typically OK because you will probably only need to change the AI plugin file if you change the app's name, description, or auth—significant changes. For most standard changes to improve the app, you can make them and keep the app live.

The future of AI

At Dart, we have been building a task and project management tool that utilizes AI for a while. Integrating with ChatGPT was an exciting next step in this process. It’s a natural fit because ChatGPT is the future of AI-based chat, and Dart is the future of AI-based project management.

If you’re interested in learning more, check out this post about what lessons I learned from building the integration and what I got from it (hint—lots of new users!) Or check out Dart here.