Search code examples
javascriptnode.jsglob

How to copy multiple SVG files into a templated react component. NodeJs?


Struggling to wrap my head around how I might achieve this issue.

I have roughly 500 SVG icons that I'd like to copy it's contents into a templated react component then save that .js file out as the SVG's name... How can I achieve this?

Here is an example of an AddressBook.svg

<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 70 70" height={height}><g ><g id="icons"> <circle fill={background} cx="35" cy="35" r="34"/><path fill={border} d="M35,70A35,35,0,1,1,70,35,35,35,0,0,1,35,70ZM35,2A33,33,0,1,0,68,35,33,33,0,0,0,35,2Z"/><path fill={icon} d="M23,38H21.5A2.79,2.79,0,0,1,19,35V29a1,1,0,0,1,2,0v6c0,.61.33,1,.5,1H23a1,1,0,0,1,0,2Z"/><path fill={icon} d="M23,47H21.5A2.79,2.79,0,0,1,19,44V38a1,1,0,0,1,2,0v6c0,.61.33,1,.5,1H23a1,1,0,0,1,0,2Z"/><path fill={icon} d="M23,29H21.5A2.79,2.79,0,0,1,19,26V19a1,1,0,0,1,2,0v7c0,.61.33,1,.5,1H23a1,1,0,0,1,0,2Z"/><path fill={icon} d="M50,54H22a3,3,0,0,1-3-3V47a1,1,0,0,1,2,0v4a1,1,0,0,0,1,1H49V22H23c-2.63,0-4-1.51-4-3s1.37-3,4-3H48a1,1,0,0,1,1,1v3h1a1,1,0,0,1,1,1V53A1,1,0,0,1,50,54ZM23,18c-1.3,0-2,.52-2,1s.7,1,2,1H47V18Z"/><path fill={icon} d="M43,44H29a1,1,0,0,1-.71-.3A1,1,0,0,1,28,43s0-.4,0-1a4.67,4.67,0,0,1,3.7-5c.6-.24,1.3-.75,1.3-1s0-.24-.18-.49A5.72,5.72,0,0,1,32,32a4,4,0,0,1,8,0,5.72,5.72,0,0,1-.82,3.51c-.16.25-.18.29-.18.49s.7.81,1.3,1A4.66,4.66,0,0,1,44,42c0,.57,0,1,0,1a1,1,0,0,1-.29.72A1,1,0,0,1,43,44ZM30,42H42a2.68,2.68,0,0,0-2.24-3l-.11,0c-.27-.1-2.65-1-2.65-2.94a2.57,2.57,0,0,1,.49-1.55A3.83,3.83,0,0,0,38,32a2,2,0,0,0-4,0,3.83,3.83,0,0,0,.51,2.45A2.57,2.57,0,0,1,35,36c0,1.9-2.38,2.84-2.65,2.94l-.11,0A2.68,2.68,0,0,0,30,42Z"/></g></g></svg>

that would be copied into the react template, template.js, in place of INSERTHERE

import React from 'react';

function SVGNAME({background, border, icon, height}) {
  return (
    *INSERTHERE*
  );
}

SVGNAME.defaultProps = {
  background: 'transparent',
  border: 'transparent',
  icon: '#000',
  height: 70
};

export default SVGNAME;

while replacing SVGNAME with the file name of the svg.

I found a few scripts online that replace a string within a group of files, but it seems to replace one string rather than each unique string (being the svg file). I was looking at this question here: Replace a string in a file with nodejs


Solution

  • try that:

    'use strict';
    
    const fs = require('fs');
    
    const inputDirectory = './svgs';
    const outputDirectory = './output';
    
    // Read every file from input directory.
    fs.readdir(inputDirectory, (err, files) => {
      if (err) {
        console.error(error);
        return;
      }
    
      // Process each file one by one.
      files.forEach(file => {
        // Read svg file from the disk
        const fileContent = fs.readFileSync(`${inputDirectory}/${file}`, 'utf8');
        const template = `import React from 'react';
    
    function SVGNAME({background, border, icon, height}) {
      return (
        *INSERTHERE*
      );
    }
    
    SVGNAME.defaultProps = {
      background: 'transparent',
      border: 'transparent',
      icon: '#000',
      height: 70
    };
    
    export default SVGNAME;`;
    
        // Replace placeholders in your template with values.
        const newFileContent = template
          .replace('*INSERTHERE*', fileContent)
    
          // SVGNAME needs to be replaced three times so regexp can be used
          .replace(/SVGNAME/g, file);
    
        // Write file to disk.
        fs.writeFileSync(`${outputDirectory}/${file.replace('.svg', '.js')}`, newFileContent);
      });
    });