tutorial // Jul 01, 2022
How to Generate Random Project Names with JavaScript
How to generate a random, hyphenated project name string from a list of adverbs and animals for use with user generated content.

For this tutorial, we're going to use CheatCode's full-stack JavaScript framework, Joystick. Joystick brings together a front-end UI framework with a Node.js back-end for building apps.
To begin, we'll want to install Joystick via NPM. Make sure you're using Node.js 16+ before installing to ensure compatibility (give this tutorial a read first if you need to learn how to install Node.js or run multiple versions on your computer):
Terminal
npm i -g @joystick.js/cli
This will install Joystick globally on your computer. Once installed, next, let's create a fresh project:
Terminal
joystick create app
After a few seconds, you will see a message logged out to cd
into your new project and run joystick start
:
Terminal
cd app && joystick start
After this, your app should be running and we're ready to get started.
Gathering source data
In order to generate a random project name, we'll need some random data to use as the source for names. While you can use any name you'd like, for this tutorial, we're going to source two lists from this helpful repo on Github: a list of adverbs and a list of animals. There are some other lists in that repo, too, so feel free to experiment or create your own.
Once you've picked out the lists you want to use—assuming you're using the lists from the link above—we'll want to pull them into our project and format them for use in our code. In the project we just created with joystick app
, we want to create two files in the /lib
folder: /lib/adverbs.js
and /lib/animals.js
:
/lib/adverbs.js
export default [
'abnormally',
'absentmindedly',
'accidentally',
'acidly',
'actually',
...
];
/lib/animals.js
export default [
'Aardvark',
'African Elephant',
'African Tree Pangolin',
'Albatross',
'Alligator',
...
];
Here, we've truncated the lists due to their length but you will want to input the full lists for your files. The two files above can be found formatted like the code blocks above here.
Once you have those files in your /lib
folder, we can move on to the name generator.
Writing a name generator function
Our name generator function will have three steps to it:
- Picking out a random adverb and animal name from our lists.
- Formatting both names, shifting them to be all lowecase and replacing any spaces with
-
hyphens. - Concatenating or joining together the lowercased, hyphenated versions into one name.
Let's take a look at the full function and step through it (it will be easier to understand as we're going to compose together function calls).
/lib/generateProjectName.js
import adverbs from "./adverbs";
import animals from "./animals";
const lowercaseAndSlugify = (string = '') => {
return string.toLowerCase().replace(/ /g, '-').replace('--', '-').trim();
};
const getRandomArrayItem = (array = []) => {
return array[Math.floor(Math.random() * (array.length - 1))];
};
export default () => {
const adverb = lowercaseAndSlugify(getRandomArrayItem(adverbs));
const animal = lowercaseAndSlugify(getRandomArrayItem(animals));
return `${adverb}-${animal}`;
};
Starting at the top, we add two imports to our file: one for our adverbs.js
file and one for our animals.js
file in the same folder. Down at the bottom of our file, we add a default export of our function.
Inside, starting with our adverb
, we compose together two function calls defined above of our main function. In JavaScript, function calls work similar to a math problem, evaluation from the inside first to the outside last.
Here, our innermost call is to a function getRandomArrayItem()
, which, like the name implies is designed to get a random item from some array we pass it. In this case, we're passing in the adverbs
list we imported up top. Looking at that getRandomArrayItem()
function, we take in our array
and return a line that says "select the item in the passed array
at this random index array[someRandomIndex]
."
To get that random index, we call to Math.random()
which gives us a random number between 0
and 1
and then multiply it by the length of our array
, subtracting 1. We do this because we'll get a number like 0.5121
from Math.random()
which when multiplied by the length of our array, will give us a number between 0
and the length of our array (i.e., a random index of an item in that array). For example, if our array
length was 25
and we got back 0.5121
from Math.random()
, our final number would be 12.2904
(24 * 0.5121
).
Because we want a flat integer and not a decimal or "float" number, we take the result of this multiplication and pass it to Math.floor()
which will round the resulting number down to the closest whole number, or in the example above, 12
. Passing this like array[12]
, we'd expect to get back the value at index 12
in the passed array.
Once we get back our random value, the next chunk of work we need to do to make the value usable in our project name (we're going for a name like advantageous-advark
), we want to lowercase it and then replace any spaces with a -
.
Above in the lowercaseAndSlugify
function, we get this done by taking in the passed string
as an argument and then immediately call .toLowerCase()
on it, chaining a call to .replace(/ /g, '-')
to say "globally in this string, replace all spaces with a -
character" followed immediately by a .replace()
for any accidental --
double-hyphens created from double spaces in names with a single -
hyphen. Finally, we chain one last call on the end to .trim()
to make sure we've eliminated any unnecessary spaces.
That's it for formatting. Back down in our exported function, we repeat this chain of events to get our animal
, passing in the animals
array to get a random value and format it. With both our random adverb
and animal
, we return a concatenated string from our function, joining the two variables together with a -
hyphen using JavaScript string interpolation.
That's it for generating our name! Now, let's wire it up to our UI and put it to use.
Putting the generator to use
This part is pretty simple. To test out our function, we're going to wire up a Joystick component. To do it, we're going to replace the existing code in /ui/pages/index/index.js
(this file was automatically generated when we ran joystick create app
earlier) with the following:
/ui/pages/index/index.js
import ui from '@joystick.js/ui';
import generateProjectName from '../../../lib/generateProjectName';
const Index = ui.component({
state: {
projectName: null,
},
events: {
'click button': (event, component) => {
component.setState({ projectName: generateProjectName() });
},
},
render: ({ when, state }) => {
return `
<div>
<button>Generate a Project Name</button>
${when(state.projectName, `
<h1>${state.projectName}</h1>
`)}
</div>
`;
},
});
export default Index;
Up top, we import the ui
object from @joystick.js/ui
which gives us access to the ui.component()
method for creating our component along with our generateProjectName
function from our /lib
folder. Below this, we create our component and store it in a variable Index
which is exported from our file at the bottom (this file is already wired up to the router in our app so we don't need to do anything else to make it work).
Focusing on the component itself, down in the render()
function we return a string of HTML to render for our component. Inside, we return a <div></div>
tag with a <button></button>
and a special call to when()
a function passed to the render()
function of Joystick components (known as the when
"render function").
That function is designed to render some HTML when
some condition is met. Here, we check to see if the state.projectName
value is defined. Here, state
is pulled from the component instance passed to the component's render()
function (the same place we plucked when()
from). That state can be set by default on our component via the state
property set on the object passed to ui.component()
.
Above, we do that by default setting projectName
on state to null
. In other words, when our component first loads up state.projectName
is equal to null
, so our call to when()
down in our render()
function wont' render the HTML passed as the second argument to it (our state.projectName
value wrapped in an <h1></h1>
tag).
To change this value, we need to call to our component's .setState()
method. Here, we do that in response to a click
event on the button
inside of our component. Up in the events
object passed to the options for ui.component()
, we've defined an event listener for a click
event on all button
elements in our component (just one in this case).
Inside of the function passed to the listener definition click button
, we expect to get the DOM event
as the first argument and then the component
instance as the second argument. On that component
instance, we get access to a function .setState()
which we can call to update values on our component's state
object. To .setState()
we pass an object with all of the values we want to update as properties. Here, we want to set projectName
equal to a random project name, so we set it equal to a call to generateProjectName()
.
The end result is that now, every time we click on our button, we'll set projectName
to a new random name and our when()
will render that name to the screen. That's it!
Wrapping up
In this tutorial, we learned how to generate a random project name in JavaScript. We learned how to write a function that can select random values from an array as well as a function for formatting the selected random value to be all-lowercase and stringified. Next, we learned how to concatenate our random values into a single string and return them from a function. Finally, we learned how to call our function and use its value to display inside of a Joystick component.