My FeedDiscussionsHeadless CMS
New
Sign in
Log inSign up
Learn more about Hashnode Headless CMSHashnode Headless CMS
Collaborate seamlessly with Hashnode Headless CMS for Enterprise.
Upgrade ✨Learn more
I made an app that publishes your blog posts to multiple platforms at once.

I made an app that publishes your blog posts to multiple platforms at once.

Shaquil Hansford's photo
Shaquil Hansford
·Apr 2, 2021·

5 min read

Blogging is one of the most powerful tools in your toolbox as a developer, whether you're an entrepreneur or a member of a team. But as someone whose career path requires constant learning and growth, your most precious resource is time--and blogging takes up a lot of time.

Even worse, there are so many platforms to choose from. Should you go with Medium, Dev.to, Hashnode, or a self-provided solution like Ghost CMS?

With OnePush, you don't have to make that choice anymore.

OnePush.blog lets you link your Medium, Dev, Hashnode and Ghost accounts together in one place, so that you can write your posts in one editor and publish them on any combination of platforms that you want--all with the push of one button.

In fact, I'm writing this from OnePush right now, and posting it to Medium, Dev, Hashnode and Ghost! I mean... if Hashnode's moderators will let this through.

Preview

A Technical Look at the Features

While the above description tells you all you need to know about the app as a user, it doesn't detail the process of actually constructing the app.

From a developer's standpoint, I had two issues to worry about: Providing a simple but informative frontend for the users, and a thorough and precise backend for the platforms they will be publishing to.

On the frontend, I had to create buttons, inputs and checkboxes that essentially give the user a tutorial on how the platform works, while also being easy enough to jump into if you're not confused. This was a bit complicated, and I ended up conceding in the mission a little when it came to teaching users how to connect OnePush to their accounts on other platforms.

You see, each popular blogging platform has its own unique way of implementing what is essentially the same solution to the problem of integrating external apps. They use JSON web tokens, which you generate by going through the settings in your account--but some of them also need other tokens which cannot be generated through their user interface.

Worse, each of them hides their API token settings in different parts of their UI's, and there isn't any simple way to explain this to a user from OnePush's perspective other than to say, "Hey, go into your account and look around for tokens. If you find them, paste them here.

API keys

In my custom backend, I had to not only craft fetch requests for each API endpoint on each platform that a user can post on, but I had to build robust error-handling systems. It's incredibly vital, especially when you're posting to an existing audience, that you know if any issues happened with posting your content, and that you have a URL to the content immediately so you can make sure it came out right.

All I can say after two weeks of this work is that Error Handling Engineer should be a full-time salaried position.

Tech Stack

So you know what OnePush is, and you know why I built it--but as a coder yourself, you may be interested in how I built it.

Well, I think everyone's natural tendency, myself included, is to focus intensely on understanding the problem we're trying to solve, and then throwing solutions at it until one sticks. While this is admirable, it is a bit irrational, and can at times even be dangerous.

Metaphorically speaking, it's like seeing a flame, identifying the source of it, and dumping water on it. That may seem like a fine enough strategy at first, but fire extinguishers exist for a reason. There may have even been one on the wall beside you, but you were so focused on rapidly trying out a solution that you ignored the better one waiting right there.

With this in mind, I decided that, even though React seems like a fine enough solution for building the frontend UI, it may not actually be quite enough. In its current state, the app's UI won't change very much at all, and any users will expect their text editor to pop up as quickly is possible so they can get writing. I also wanted to do rapid prototyping by testing API calls from the UI without having to build an entire backend.

NextJS was the obvious solution.

Express and Node

Node

But that doesn't mean I didn't eventually want to build my own backend. I knew it would allow me more flexibility for implementing future features if I did so, and I didn't want to shoot myself in the foot. In a world that rightfully reminds everyone of YAGNI (You Ain't Gonna Need It) whenever thoughts of future-proofing your code come up, it's important to remember that there's nothing wrong with a little upfront work to increase scalability.

I deployed my Node backend on Render.com for simplicity's sake, though it's slightly more expensive than Digital Ocean. In return for building out my own API and backend, I will be able to implement packages like Passport and bCrypt in the future for user accounts and login sessions.

This is very necessary, as any users of the app will soon notice. When you enter your API keys, they are remembered; but currently your blog posts aren't saved to OnePush for later editing or deleting, and if you use a different browser or clear your localstorage, you'll have to manually re-enter all that data.

We'll have logins one day soon!

Tired

What's Next?

So what's next?

A small break, please. Goodness!

But aside from that, I've got a ton of features I can already think of. Aside from implementing a user account system, I do want people to use OnePush as the "One Source of Truth," which isn't possible yet, and won't be possible until you can view and edit your posts from within OnePush. Heck, you can't even save drafts yet.

But that'll all be coming very soon. If you want to use this app, head to OnePush.blog. If you have any suggestions, I'm on twitter! @shaquilhansford.

Thanks for reading!