skip to Main Content
  • Strapi Version: 4.3.0
  • Operating System: Ubuntu 20.04
  • Database: SQLite
  • Node Version: 16.16
  • NPM Version: 8.11.0
  • Yarn Version: 1.22.19

I have created Preview button for an article collection type. I’m using the Strapi blog template. I managed to make the Preview button appear in the Content Manager. I hard coded the link to be opened when you click the Preview button and it works. Now, I want the plugin to use a link with environment variables instead of a hard coded link. I don’t know how I can access the environment variables in the source code for the plugin.

My objective:

I want to replace

href={`http://localhost:3000?secret=abc&slug=${initialData.slug}`}

with

href={${CLIENT_FRONTEND_URL}?secret=${CLIENT_SECRET}&slug=${initialData.slug}`}

in ./src/plugins/previewbtn/admin/src/components/PreviewLink/index.js

where CLIENT_FRONTEND_URL and CLIENT_SECRET are environment variables declared like so in .env:

CLIENT_FRONTEND_URL=http://localhost:3000
CLIENT_PREVIEW_SECRET=abc

Here’s a rundown of the code I used:

First, I created a strapi app using the blog template, then created a plugin.

// Create strapi app named backend with a blog template
 $  yarn create strapi-app backend  --quickstart --template @strapi/[email protected] blog && cd backend

// Create plugin
$ yarn strapi generate

Next, I created a PreviewLink file to provide a link for the Preview button

// ./src/plugins/previewbtn/admin/src/components/PreviewLink/index.js
import React from 'react';
import { useCMEditViewDataManager } from '@strapi/helper-plugin';
import Eye from '@strapi/icons/Eye';
import { LinkButton } from '@strapi/design-system/LinkButton';

const PreviewLink = () => {
  const {initialData} = useCMEditViewDataManager();
  if (!initialData.slug) {
    return null;
  }

  return (
    <LinkButton
      size="S"
      startIcon={<Eye/>}
      style={{width: '100%'}}
      href={`http://localhost:3000?secret=abc&slug=${initialData.slug}`}
      variant="secondary"
      target="_blank"
      rel="noopener noreferrer"
      title="page preview"
    >Preview
    </LinkButton>
  );
};

export default PreviewLink;

Then I edited this pregenerated file in the bootstrap(app) { ... } section only

// ./src/plugins/previewbtn/admin/src/index.js
import { prefixPluginTranslations } from '@strapi/helper-plugin';
import pluginPkg from '../../package.json';
import pluginId from './pluginId';
import Initializer from './components/Initializer';
import PreviewLink from './components/PreviewLink';
import PluginIcon from './components/PluginIcon';

const name = pluginPkg.strapi.name;
export default {
  register(app) {
    app.addMenuLink({
      to: `/plugins/${pluginId}`,
      icon: PluginIcon,
      intlLabel: {
        id: `${pluginId}.plugin.name`,
        defaultMessage: name,
      },
      Component: async () => {
        const component = await import(/* webpackChunkName: "[request]" */ './pages/App');
        return component;
      },

      permissions: [
        // Uncomment to set the permissions of the plugin here
        // {
        //   action: '', // the action name should be plugin::plugin-name.actionType
        //   subject: null,
        // },
      ],
    });

    app.registerPlugin({
      id: pluginId,
      initializer: Initializer,
      isReady: false,
      name,
    });
  },

  bootstrap(app) {
    app.injectContentManagerComponent('editView', 'right-links', {
      name: 'preview-link',
      Component: PreviewLink
    });
  },

  async registerTrads({ locales }) {
    const importedTrads = await Promise.all(
      locales.map(locale => {
        return import(
          /* webpackChunkName: "translation-[request]" */ `./translations/${locale}.json`
        )

          .then(({ default: data }) => {
            return {
              data: prefixPluginTranslations(data, pluginId),
              locale,
            };
          })

          .catch(() => {
            return {
              data: {},
              locale,
            };
          });
      })
    );
    return Promise.resolve(importedTrads);
  },
};

And lastly this created this file to enable the plugin Reference

// ./config/plugins.js
module.exports = {
    // ...
    'preview-btn': {
      enabled: true,
      resolve: './src/plugins/previewbtn' // path to plugin folder
    },
    // ...
  }


2

Answers


  1. Chosen as BEST ANSWER

    I solved this by adding a custom webpack configuration to enable Strapi's admin frontend to access the environment variables as global variables.

    I renamed ./src/admin/webpack.example.config.js to ./src/admin/webpack.config.js. Refer to the v4 code migration: Updating the webpack configuration from the Official Strapi v4 Documentation.

    I then inserted the following code, with help from Official webpack docs: DefinePlugin | webpack :

    // ./src/admin/webpack.config.js
    'use strict';
    
    /* eslint-disable no-unused-vars */
    module.exports = (config, webpack) => {
      // Note: we provide webpack above so you should not `require` it
      // Perform customizations to webpack config
      // Important: return the modified config
      config.plugins.push(
        new webpack.DefinePlugin({
          CLIENT_FRONTEND_URL: JSON.stringify(process.env.CLIENT_FRONTEND_URL),
          CLIENT_PREVIEW_SECRET: JSON.stringify(process.env.CLIENT_PREVIEW_SECRET),
        })
      )
    
      return config;
    };
    

    I rebuilt my app afterwards and it worked.


  2. You shouldn’t have to change the webpack config just find .env file in the root directory
    add

    AWS_ACCESS_KEY_ID = your key here
    

    then just import by
    accessKeyId: env('AWS_ACCESS_KEY_ID')

    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search