The system is designed to be easily extensible. Each provider need to implement multiple things. There are two main options:

  • Implement a social media provider (oAuth2)
  • Implement a publishing provider (Token)
  1. The backend logic:

    • Define DTO for the settings of the provider
    • Generate an authentication URL
    • Authenticate the user from the callback
    • Refresh the user token
  2. The frontend logic:

    • Implement the settings page
    • Implement the preview page
    • Upload the provider image

Social Media

Backend

For our example, we will use the X provider.

  1. First, we need to create a DTO for the settings of the provider.
    head over to nestjs-libraries/src/dtos/posts/providers-settings And create a new file x-provider-settings.dto.ts
    (you don’t have to create a DTO if there are no settings)

    Once created head over to nestjs-libraries/src/dtos/posts/providers-settings/all.providers.settings.ts And add the new DTO.

    Head to libraries/nestjs-libraries/src/dtos/posts/create.post.dto.ts
    look for the discriminator and add another line in the format of
create.post.dto.ts
{ value: DTOClassName, name: 'providerName' },
  1. head over to libraries/nestjs-libraries/src/integrations/social
    And create a new provider file providerName.provider.ts
    The content of the file should look like this:
import {
  AuthTokenDetails,
  PostDetails,
  PostResponse,
  SocialProvider,
} from '@gitroom/nestjs-libraries/integrations/social/social.integrations.interface';

export class XProvider implements SocialProvider {
  identifier = 'providerName';
  name = 'Provider Name';
  async refreshToken(refreshToken: string): Promise<AuthTokenDetails> {
    ...refresh the token
  }

  async generateAuthUrl() {
    ...generate the auth url
  }

  async authenticate(params: { code: string; codeVerifier: string }) {
    ...authenticate the user
  }

  async post(
    id: string,
    accessToken: string,
    postDetails: PostDetails<DTOClassName>[]
  ): Promise<PostResponse[]> {
    ...post the content
  }
}

Take a look at the exising providers to see how to implement the methods.

Custom functions

You might want to create custom functions for the providers for example: get available orgs, get available pages, etc.
You can create a public function in the provider for example organizations and later call it from a special hook from the frontend.

Integration Manager

Open libraries/nestjs-libraries/src/integrations/integration.manager.ts And add the new provider to either socialIntegrationList (oAuth2) or articleIntegrationList (Token)


Frontend

  1. Head over to apps/frontend/src/components/launches/providers Create a new folder with the providerName
    Add a new file providerName.provider.tsx
    The content of the file should look like this:
providerName.provider.tsx
import { FC } from 'react';
import { withProvider } from '@gitroom/frontend/components/launches/providers/high.order.provider';
import { useSettings } from '@gitroom/frontend/components/launches/helpers/use.values';
import { useIntegration } from '@gitroom/frontend/components/launches/helpers/use.integration';

const ProviderPreview: FC = () => {
  const { value } = useIntegration();
  const settings = useSettings();

  return (
    ...Preview
  );
};

const ProviderSettings: FC = () => {
  const form = useSettings();
  const { date } = useIntegration();
  return (
    ...Settings
  );
};

export default withProvider(DevtoSettings, DevtoPreview, DTOClassName);

If you want to use a custom function for the provider you can use the useCustomProviderFunction hook.

import { useCustomProviderFunction } from '@gitroom/frontend/components/launches/helpers/use.custom.provider.function';
import { useCallback } from 'react';
const customFunc = useCustomProviderFunction();

// and use it like that:
const getOrgs = useCallback(() => {
  customFunc.get('organizations', {
      anyKey: 'anyValue'
  })
}, []);

It will automatically interact with the right provider saved for the user.

You can look at the other integration to understand what data to put inside.

  1. Open apps/frontend/src/components/launches/providers/show.all.providers.tsx And add the new provider to the list.
show.all.providers.tsx
    {identifier: 'providerName', component: DefaultImportFromHighOrderProvider},