Design Challenge 001: Building a Flexible Request Type Builder
Join the discussion and improve your software design skills by solving real-world problems.
As mentioned in the previous issue of the newsletter, I will be changing the format a bit. In each issue, I’ll describe a problem from my recent project and ask you to think of a solution. In the next issue, I will share my own solution. It might not be the best, but it should be good enough to demonstrate the idea and design pattern for the case.
I’m not sure how many cases I can come up with, but I hope this can be a sustainable practice that benefits other developers, especially those who want to hone their software design skills.
Here's the first one. I will share some context about the business logic, and you can use the techniques you’re familiar with to implement it. You don’t have to provide the working code to me (although you can share a CodeSandbox or GitHub repo), but you can share some pseudo code or your thoughts.
In a service desk application, admins sometimes need to add new request types to the system as more scenarios are discovered. On the project settings page, there is a "Create Request Type" button which links to a Request Type Builder page. When clicked, a new page appears, allowing the user to create a Request Type by choosing a template from a list.
For example, in an HR context, a Request Type could be Employee Onboarding, Asking for Leave, etc. In an IT context, it could be Getting a Guest Pass, Requesting a New VPN Account, Testing a Mobile Device, etc.
The page also provides many other functionalities, such as allowing the user to search by template name, preview a template, and then choose one to use in their project.
This functionality is useful for existing projects where an admin wants to customize more. The Request Type Builder is also helpful when an admin is creating a new project. We want to share the functionality of searching by template name, selecting a template, and previewing a template in the new project creation scenarios.
However, there are some small UI differences. The header, for example, is not identical for these two screens.
In the old implementation, the logic for the Request Type component is something like this:
const TemplateSelector = ({ templates }) => {
return (
<div>
<SearchBar />
<Category />
<TemplateList templates={templates} />
</div>
);
};
const RequestTypeBuilder = ({ renderedIn }) => {
const { templates } = useTemplates(); // fetch templates from remote
const { user } = useCurrentUser();
const getHeader = () => {
switch (renderedIn) {
case "creating_new_project":
return (
<div>
<h1>Welcome, {user.name}</h1>
<p>Choose the request ...</p>
</div>
);
case "creating_new_request_type":
return (
<div>
<h1>Select a request type</h1>
<p>Select a template ...</p>
</div>
);
default:
return null;
}
};
return (
<div>
{getHeader()}
<TemplateSelector templates={templates} />
</div>
);
};
The code above uses renderedIn
as a prop to distinguish which type of header
should be used in the RequestTypeBuilder
. If it’s for creating_new_project
, it renders Welcome,...
and for creating_new_request_type
, it shows Select a request type...
.
Now, there is another requirement change. Another team also wants to use the Request Type Builder, and they have a different header to show on the top of the page.
What would you do to reflect this change on top of the current implementation? What options do you have, and how would you pick the one that suits your needs?
Please comment and share your thoughts. I’ll reveal mine in the next issue.
This is an interesting exercise!
I don't have much experience with React but I'll give it a go.
I'd first make the change easy by extracting one component for each of the existing types of headers and a map of header components for each type:
https://gist.github.com/alonsogarciapablo/73ca613d8547690dff37f950971c7411#file-refactor01-js
Adding new types of headers would now be as simple as defining a new header component and setting them up in the `headerComponents` map. If the new header is pretty similar to the two existing one (eg: has a title and a description), we could extract a generic `Header` component and use it for each of the headers:
https://gist.github.com/alonsogarciapablo/73ca613d8547690dff37f950971c7411#file-refactor02-js
This way it'd be even easier to add new headers.
Hope my React code makes any sense 🤣